DarkBASIC Professional

Quake III BSP using DBPro

DarkBASIC Professional is a programming language and front end to DirectX rolled into one package. It is extensible by plug-in DLL, which makes it an excellent development language. Its chief drawback is the IDE, which is a little buggy with respect to saving files during compile. There are alternative IDEs available, but I have no experience with them.


The Game Creators website

Quake III BSP using DBPro

DBPro can be downloaded and used without purchase for evaluation purposes. The only limitations are that there is a watermark, and you cannot use plug-ins. The current price is 89USD, which is a bargain.

It is not a replacement for learning game programming, but it is a nice RAD tool to use in learning game programming. When I downloaded it, I was able to use QIII maps I had made using Quark. There is a nice (but flawed) FPS tutorial that uses BSP maps. DBPro can load from PK3 files, which is great. I used MD2 models from Quake II, and also DBPro came bundled with some free models in X format.

Quake III BSP using DBPro

Out of the box, DBPro is quite capable of creating a top notch video game. Certainly, it is at least as capable as some of the other options that I have tried. (Torque, PopCap and Blender, to be exact.) At the time of this writing, The Game Creators and Microsoft have made a C++ package available that is the core of DarkBASIC Professional in the form of a C++ Game Developer's Kit. Also of note is Microsoft's XNA, which can be used to develop code for the XBox360.

DBPro Advanced Terrain

There is a very powerful Advanced Terrain system in DBPro. This particular area was created using DTED (Digital Terrain Elevation Data) data for the area of Brest, Belarus. Although I am still using the female ensign from Quake II, the intent is to replace her with a Soviet Rifleman, or Red Standard Guard, perhaps. This game has elements of RTS, RPG, and FPS. It is my most complex DBPro application, and the reason I even bother with most of the other stuff I do in DBPro.

DBPro Audio DSP

This is a graph of a 75bps RadioTeletype (RTTY) signal. The top graph is the RAW audio signal with data point connect and also fill, which are useful aids in evaluating the signal visually. Next, is the FFT plot of that same signal. The bottom graph is an histogram of the signal. This application is a 2D graphing application at this time, but I have been slowly expanding the graphing capablilites and also multiple cameras offer alot in terms of display flexibility, which I have been using alot recently.

DBPro Data Acquisition and Display using multiple protocols

DBPro can load DLLs and this is an application that uses Dallas 1-Wire iButton Devices, NTP, TCP, FTP, and a lot more for data acquisition. The Earth, clock, gauges and the weather vane are all created programmatically, and all of the data collected from the Internet was obtained using native DBPro (FTP) and by calling Windows DLLs (Winsock, IPHelper, etc.) from DBPro. It is a cooperative open source project that I have written with another user.

DBPro ImageMagick++ plug-in

I wrote a wrapper DLL for the open source image processing API, ImageMagick++. It is a substantial API, with over 500 functions. It is documented and drops into a DBPro installation cleanly, with function highlighting, context sensitive help and example code. The wrapper is written in C++ using Visual C++ 2003. It makes heavy use of the C++ Standard Template Library, especially vectors.

DBPro ImageMagick++ plug-in

This is a montage of images created with ImageMagick++ and DBPro.

Here are some screen shots of a Rock Band clone I am working on.
RockStar Game RockStar Game
RockStar Game RockStar Game

Here is a source code file I have written consisting of some very simple DBPro helper utilities.

remstart
   					jzHelper.dba
remend
#constant TRUE          = 1
#constant FALSE         = 0
#constant NULL          = 0
#constant NULLSTR       = ""

function jzGetNextAvailableObjectID(seed as integer)
   local temp = seed

   if seed < 1 then exitfunction -1
   do
      if object exist(temp) = 0 then exitfunction temp
      inc temp
      if temp < 1 then exitfunction -1
   loop
endfunction -1

function jzGetNextAvailableImageID(seed as integer)
   local temp = seed

   if seed < 1 then exitfunction -1
   do
      if image exist(temp) = 0 then exitfunction temp
      inc temp
      if temp < 1 then exitfunction -1
   loop
endfunction -1

function jzGetNextAvailableSoundID(seed as integer)
   local temp = seed

   if seed < 1 then exitfunction -1
   do
      if sound exist(temp) = 0 then exitfunction temp
      inc temp
      if temp < 1 then exitfunction temp
   loop
endfunction -1

function jzGetNextAvailableMusicID(seed as integer)
   local temp = seed

   if seed < 1 then exitfunction -1
   do
      if music exist(temp) = 0 then exitfunction temp
      inc temp
      if temp < 1 then exitfunction temp
   loop
endfunction -1

function jzGetNextAvailableAnimationID(seed as integer)
   local temp = seed

   if seed < 1 or seed > 32 then exitfunction -1
   do
      if animation exist(temp) = 0 then exitfunction temp
      inc temp
      if temp > 32 then exitfunction -1
   loop
endfunction -1

function jzGetNextAvailableMemblockID(seed as integer)
   local temp = seed

   if seed < 1 then exitfunction -1
   do
      if memblock exist(temp) = 0 then exitfunction temp
      inc temp
      if temp < 0 then exitfunction -1
   loop
endfunction -1

remstart Signed 16 and 32 bit division by powers of two using bitmasks and shifting.
         Since these are reduction of force, they have zero error checking. All they
         would do anyway is spin their wheels and produce corrupt data. Simple tests
         reveal they are slower than division by two, at least.
remend

function jzS16DivByPow2(dividend as integer, power as integer)
   if dividend && 0x8000
      dividend = dividend .. 0xffff
      inc dividend
      dividend = dividend >> power
      dividend = dividend .. 0xffff
      inc dividend
   else
      dividend = dividend >> power
   endif
endfunction dividend

remstart function jzS32DivByPow2(dividend as DWORD, power as integer)
   if dividend && 0x80000000
      dividend = dividend .. 0xffffffff
      inc dividend
      dividend = dividend >> power
      dividend = dividend .. 0xffffffff
      inc dividend
   else
      dividend = dividend >> power
   endif
endfunction dividend
remend

function jzDiceRoll(sides as integer)
   local temp as integer

   temp = 1 + rnd(sides)
endfunction temp

remstart Here are some functions to help interface DBPro with C/C++, DLLs, and other
         "outside entities".
remend

function jzGetNextAvailableDLLID(bDown as boolean, seed as integer)
   local temp = seed

   if seed < 1 or seed > 255 then exitfunction -1
   do
      if dll exist(temp) = 0 then exitfunction temp
      if bDown = 1
         dec temp
      else
         inc temp
      endif
      if temp < 1 or temp > 255 then exitfunction -1
   loop
endfunction -1

remstart jzDupStr - Returns an n-length string consisting of the string passed.
remend

function jzDupStr(character as string, numtimes as integer)
    local buildstr as string = ""
    local i as integer

    for i = 0 to numtimes - 1
        buildstr = buildstr + character
    next i
endfunction buildstr

remstart jzGetToken - Returns the token number requested using delimiter.
remend

function jzGetToken(inputstr as string, token as integer, delimiter as string)
    local count as integer
    local found as integer = 0
    local buildstr as string = ""

    for count = 0 to len(inputstr)
        if mid$(inputstr, count) = delimiter
            inc found
            if found = token
                exitfunction buildstr
            else
                buildstr = ""
            endif
        else
            buildstr = buildstr + mid$(inputstr, count)
        endif
    next count
endfunction buildstr

remstart jzMakeASCIIZString - This function allocates memory on behalf of the
         caller. It is the caller's responsibility to delete the memory. This function
         only takes ASCII, and only produces ASCII. The function returns the pointer
         to the new string.
remend

function jzMakeASCIIZString(str1 as string)
   local pString as DWORD
   local pTemp as DWORD
   local strsize as integer
   local i as integer

   strsize = len(str1) + 1
   pString = make memory(strsize)
   fill memory pString, 0, strsize
   pTemp = pString
   for i = 1 to strsize - 1
      *pTemp = asc(mid$(str1, i))
      inc pTemp
   next i
endfunction pString

remstart jzMakeASCIIZZString - This function allocates memory on behalf of the
         caller. It is the caller's responsibility to delete the memory. This function
         only takes ASCII, and only produces ASCII. The function returns the pointer
         to the new string. It is used for formatting file type filters in Windows
         common dialog boxes, for example.
remend

function jzMakeASCIIZZString(str1 as string)
    local pString as DWORD
    local pTemp as DWORD
    local strsize as integer
    local i as integer

    strsize = len(str1) + 2
    pString = make memory(strsize)
    fill memory pString, 0, strsize
    pTemp = pString
    for i = 1 to strsize - 1
        if mid$(str1, i) = "|"
            *pTemp = 0
        else
            *pTemp = asc(mid$(str1, i))
        endif
    inc pTemp
    next i
endfunction pString

remstart jzMakeDBString - This function converts an ASCII Z string to a DBPro string.
                          it makes no memory demands on the part of the caller.
remend

function jzMakeDBString(cstring_blockID as integer)
    local ivalue as integer
    local icount as integer
    local offset as integer
    local buildstr as string

    offset = 0
    icount = 0
    buildstr = ""
    ivalue = memblock byte(cstring_blockID, offset)
    while ivalue > 0
        buildstr = buildstr + chr$(ivalue)
        inc offset
        inc icount
        if icount > 32767 then exitfunction buildstr
        ivalue = memblock byte(cstring_blockID, offset)
    endwhile
endfunction buildstr

function jzMakeDBString2(ptr as dword)
    local i as integer = 0
    local databyte as byte
    local buildstr as string = ""

    databyte = *ptr
    while databyte > 31 and databyte < 128 and i < 32768
        buildstr = buildstr + chr$(int(databyte))
        inc ptr, 1
        inc i, 1
        databyte = *ptr
    endwhile
endfunction buildstr

remstart    jzBuildPath - This function converts the double NULL terminated ASCIIZ string
            returned by GetOpenFileName into a single DB string.
remend

function jzBuildPath(pstr as DWORD)
    local numnulls as integer
    local ptr1 as DWORD
    local tempstr as string

    tempstr = ""
    ptr1 = pstr
    numnulls = 0
    while numnulls < 3
        if (*ptr1) > 0
            if tempstr = ""
                tempstr = chr$(*ptr1)
            else
                tempstr = tempstr + chr$(*ptr1)
            endif
        else
            if numnulls < 1 then tempstr = tempstr + "/"
            inc numnulls
        endif
        inc ptr1
    endwhile
endfunction tempstr

function jzMakeWordIntValue(wordvalue as word)
    local intValue as integer

    if wordvalue && 0x8000              rem This checks for a sign bit.
        intValue = wordvalue - 65536    rem Quick and dirty, but accurate...100%.
    else
        intValue = wordvalue
    endif
endfunction intValue
Hosted by www.Geocities.ws

1