Browse Source

add folder FreePascal

Mirrel 4 years ago
parent
commit
5a5b298cb3
73 changed files with 4833 additions and 501 deletions
  1. 83 0
      Zengl_SRC/demos/FreePascal/01 - Initialization/Makefile
  2. 120 0
      Zengl_SRC/demos/FreePascal/01 - Initialization/demo01.pas
  3. 24 0
      Zengl_SRC/demos/FreePascal/01 - Initialization/demo01_macosx.plist
  4. 0 0
      Zengl_SRC/demos/FreePascal/01 - Initialization/fp___.err
  5. 0 0
      Zengl_SRC/demos/FreePascal/01 - Initialization/fp___.out
  6. 3 0
      Zengl_SRC/demos/FreePascal/01 - Initialization/macosx_postbuild.sh
  7. 83 0
      Zengl_SRC/demos/FreePascal/02 - Resources/Makefile
  8. 154 0
      Zengl_SRC/demos/FreePascal/02 - Resources/demo02.pas
  9. 24 0
      Zengl_SRC/demos/FreePascal/02 - Resources/demo02_macosx.plist
  10. 10 0
      Zengl_SRC/demos/FreePascal/02 - Resources/macosx_postbuild.sh
  11. 83 0
      Zengl_SRC/demos/FreePascal/03 - Input/Makefile
  12. 157 0
      Zengl_SRC/demos/FreePascal/03 - Input/demo03.pas
  13. 24 0
      Zengl_SRC/demos/FreePascal/03 - Input/demo03_macosx.plist
  14. 5 0
      Zengl_SRC/demos/FreePascal/03 - Input/macosx_postbuild.sh
  15. 83 0
      Zengl_SRC/demos/FreePascal/04 - Screen Settings/Makefile
  16. 152 0
      Zengl_SRC/demos/FreePascal/04 - Screen Settings/demo04.pas
  17. 24 0
      Zengl_SRC/demos/FreePascal/04 - Screen Settings/demo04_macosx.plist
  18. 6 0
      Zengl_SRC/demos/FreePascal/04 - Screen Settings/macosx_postbuild.sh
  19. 83 0
      Zengl_SRC/demos/FreePascal/05 - Primitives/Makefile
  20. 91 0
      Zengl_SRC/demos/FreePascal/05 - Primitives/demo05.pas
  21. 24 0
      Zengl_SRC/demos/FreePascal/05 - Primitives/demo05_macosx.plist
  22. 3 0
      Zengl_SRC/demos/FreePascal/05 - Primitives/macosx_postbuild.sh
  23. 83 0
      Zengl_SRC/demos/FreePascal/06 - Text/Makefile
  24. 129 0
      Zengl_SRC/demos/FreePascal/06 - Text/demo06.pas
  25. 24 0
      Zengl_SRC/demos/FreePascal/06 - Text/demo06_macosx.plist
  26. 5 0
      Zengl_SRC/demos/FreePascal/06 - Text/macosx_postbuild.sh
  27. 83 0
      Zengl_SRC/demos/FreePascal/07 - Sprites/Makefile
  28. 256 0
      Zengl_SRC/demos/FreePascal/07 - Sprites/demo07.pas
  29. 24 0
      Zengl_SRC/demos/FreePascal/07 - Sprites/demo07_macosx.plist
  30. 10 0
      Zengl_SRC/demos/FreePascal/07 - Sprites/macosx_postbuild.sh
  31. 83 0
      Zengl_SRC/demos/FreePascal/08 - Sprite Engine/Makefile
  32. 202 0
      Zengl_SRC/demos/FreePascal/08 - Sprite Engine/demo08.pas
  33. 24 0
      Zengl_SRC/demos/FreePascal/08 - Sprite Engine/demo08_macosx.plist
  34. 7 0
      Zengl_SRC/demos/FreePascal/08 - Sprite Engine/macosx_postbuild.sh
  35. 83 0
      Zengl_SRC/demos/FreePascal/09 - Sprite Engine(Classes)/Makefile
  36. 206 0
      Zengl_SRC/demos/FreePascal/09 - Sprite Engine(Classes)/demo09.pas
  37. 24 0
      Zengl_SRC/demos/FreePascal/09 - Sprite Engine(Classes)/demo09_macosx.plist
  38. 7 0
      Zengl_SRC/demos/FreePascal/09 - Sprite Engine(Classes)/macosx_postbuild.sh
  39. 83 0
      Zengl_SRC/demos/FreePascal/10 - Tiles/Makefile
  40. 90 0
      Zengl_SRC/demos/FreePascal/10 - Tiles/demo10.pas
  41. 24 0
      Zengl_SRC/demos/FreePascal/10 - Tiles/demo10_macosx.plist
  42. 7 0
      Zengl_SRC/demos/FreePascal/10 - Tiles/macosx_postbuild.sh
  43. 83 0
      Zengl_SRC/demos/FreePascal/11 - Grid/Makefile
  44. 100 0
      Zengl_SRC/demos/FreePascal/11 - Grid/demo11.pas
  45. 24 0
      Zengl_SRC/demos/FreePascal/11 - Grid/demo11_macosx.plist
  46. 9 0
      Zengl_SRC/demos/FreePascal/11 - Grid/macosx_postbuild.sh
  47. 83 0
      Zengl_SRC/demos/FreePascal/12 - Render into Texture/Makefile
  48. 90 0
      Zengl_SRC/demos/FreePascal/12 - Render into Texture/demo12.pas
  49. 24 0
      Zengl_SRC/demos/FreePascal/12 - Render into Texture/demo12_macosx.plist
  50. 6 0
      Zengl_SRC/demos/FreePascal/12 - Render into Texture/macosx_postbuild.sh
  51. 83 0
      Zengl_SRC/demos/FreePascal/13 - Particles/Makefile
  52. 131 0
      Zengl_SRC/demos/FreePascal/13 - Particles/demo13.pas
  53. 24 0
      Zengl_SRC/demos/FreePascal/13 - Particles/demo13_macosx.plist
  54. 8 0
      Zengl_SRC/demos/FreePascal/13 - Particles/macosx_postbuild.sh
  55. 83 0
      Zengl_SRC/demos/FreePascal/14 - Sound/Makefile
  56. 167 0
      Zengl_SRC/demos/FreePascal/14 - Sound/demo14.pas
  57. 24 0
      Zengl_SRC/demos/FreePascal/14 - Sound/demo14_macosx.plist
  58. 9 0
      Zengl_SRC/demos/FreePascal/14 - Sound/macosx_postbuild.sh
  59. 83 0
      Zengl_SRC/demos/FreePascal/15 - Video/Makefile
  60. 94 0
      Zengl_SRC/demos/FreePascal/15 - Video/demo15.pas
  61. 24 0
      Zengl_SRC/demos/FreePascal/15 - Video/demo15_macosx.plist
  62. 6 0
      Zengl_SRC/demos/FreePascal/15 - Video/macosx_postbuild.sh
  63. 86 0
      Zengl_SRC/demos/FreePascal/16 - Physics/Makefile
  64. 232 0
      Zengl_SRC/demos/FreePascal/16 - Physics/demo16.pas
  65. 24 0
      Zengl_SRC/demos/FreePascal/16 - Physics/demo16_macosx.plist
  66. 5 0
      Zengl_SRC/demos/FreePascal/16 - Physics/macosx_postbuild.sh
  67. 86 0
      Zengl_SRC/demos/FreePascal/17 - Menu(touch menu)/Makefile
  68. 141 0
      Zengl_SRC/demos/FreePascal/17 - Menu(touch menu)/demo17.pas
  69. 24 0
      Zengl_SRC/demos/FreePascal/17 - Menu(touch menu)/demo17_macosx.plist
  70. 5 0
      Zengl_SRC/demos/FreePascal/17 - Menu(touch menu)/macosx_postbuild.sh
  71. 150 0
      Zengl_SRC/demos/FreePascal/Makefile
  72. 232 500
      Zengl_SRC/extra/zglChipmunk.pas
  73. 3 1
      Zengl_SRC/src/zgl_application.pas

+ 83 - 0
Zengl_SRC/demos/FreePascal/01 - Initialization/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo01.pas
+TARGET  = demo01
+TARGETW = demo01.exe
+TARGETM = demo01
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 120 - 0
Zengl_SRC/demos/FreePascal/01 - Initialization/demo01.pas

@@ -0,0 +1,120 @@
+program demo01;
+
+// RU: Этот файл содержит некоторые настройки(например использовать ли статическую компиляцию) и определения ОС под которую происходит компиляция.
+// EN: This file contains some options(e.g. whether to use static compilation) and defines of OS for which is compilation going.
+{$I zglCustomConfig.cfg}
+
+uses
+  {$IFDEF USE_ZENGL_STATIC}
+  // RU: При использовании статической компиляции необходимо подключать модули ZenGL содержащие необходимый функционал.
+  // EN: Using static compilation needs to use ZenGL units with needed functionality.
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_utils
+  {$ELSE}
+  // RU: Используя ZenGL в качестве библиотеки(so, dll или dylib) нужен всего один заголовочный файл.
+  // EN: Using ZenGL as a shared library(so, dll or dylib) needs only one header.
+  zglHeader
+  {$ENDIF}
+  ;
+
+var
+  DirApp  : UTF8String;
+  DirHome : UTF8String;
+
+  TimeStart  : Byte = 0;
+
+procedure Init;
+begin
+  // RU: Тут можно выполнять загрузку основных ресурсов.
+  // EN: Here can be loading of main resources.
+end;
+
+procedure Draw;
+begin
+  // RU: Тут "рисуем" что угодно :)
+  // EN: Here "draw" anything :)
+end;
+
+procedure Update( dt : Double );
+begin
+  // RU: Эта функция наземенима для реализация плавного движения чего-либо, т.к. точность таймеров ограничена FPS.
+  // EN: This function is the best way to implement smooth moving of something, because accuracy of timers are restricted by FPS.
+end;
+
+procedure Timer;
+begin
+  // RU: Будем в заголовке показывать количество кадров в секунду.
+  // EN: Caption will show the frames per second.
+  wnd_SetCaption( '01 - Initialization[ FPS: ' + u_IntToStr( zgl_Get( RENDER_FPS ) ) + ' ]' );
+end;
+
+procedure Quit;
+begin
+ //
+end;
+
+Begin
+  // RU: Код ниже загружает библиотеку если статическая компиляция не используется.
+  // EN: Code below loads a library if static compilation is not used.
+(*  {$IFNDEF USE_ZENGL_STATIC}
+    {$IFDEF LINUX}
+    // RU: В GNU/Linux все библиотеки принято хранить в /usr/lib, поэтому libZenGL.so должна быть предварительно установлена.
+    // Но zglLoad сначала проверить есть ли libZenGL.so рядом с исполняемым файлом.
+    //
+    // EN: In GNU/Linux all libraries placed in /usr/lib, so libZenGL.so must be installed before it will be used.
+    // But zglLoad will check first if there is libZenGL.so near executable file.
+    if not zglLoad( libZenGL ) Then exit;
+    {$ENDIF}
+    {$IFDEF WINDOWS}
+    if not zglLoad( libZenGL ) Then exit;
+    {$ENDIF}
+    {$IFDEF DARWIN}
+    // RU: libZenGL.dylib следует предварительно поместить в каталог MyApp.app/Contents/Frameworks/, где MyApp.app - Bundle вашего приложения.
+    // Также следует упомянуть, что лог-файл будет создаваться в корневом каталоге поэтому либо отключайте его, либо указывайте свой путь и имя, как описано в справке.
+    //
+    // EN: libZenGL.dylib must be placed into this directory MyApp.app/Contents/Frameworks/, where MyApp.app - Bundle of your application.
+    // Also you must know, that log-file will be created in root directory, so you must disable a log, or choose your own path and name for it. How to do this you can find in documentation.
+    if not zglLoad( libZenGL ) Then exit;
+    {$ENDIF}
+  {$ENDIF}   *)
+
+  // RU: Для загрузки/создания каких-то своих настроек/профилей/etc. можно получить путь к домашенему каталогу пользователя, или к исполняемому файлу(не работает для GNU/Linux).
+  // EN: For loading/creating your own options/profiles/etc. you can get path to user home directory, or to executable file(not works for GNU/Linux).
+  DirApp  := utf8_Copy( PAnsiChar( zgl_Get( DIRECTORY_APPLICATION ) ) );
+  DirHome := utf8_Copy( PAnsiChar( zgl_Get( DIRECTORY_HOME ) ) );
+
+  // RU: Создаем таймер с интервалом 1000мс.
+  // EN: Create a timer with interval 1000ms.
+  TimeStart := timer_Add( @Timer, 1000, start );
+
+  // RU: Регистрируем процедуру, что выполнится сразу после инициализации ZenGL.
+  // EN: Register the procedure, that will be executed after ZenGL initialization.
+  zgl_Reg( SYS_LOAD, @Init );
+  // RU: Регистрируем процедуру, где будет происходить рендер.
+  // EN: Register the render procedure.
+  zgl_Reg( SYS_DRAW, @Draw );
+  // RU: Регистрируем процедуру, которая будет принимать разницу времени между кадрами.
+  // EN: Register the procedure, that will get delta time between the frames.
+  zgl_Reg( SYS_UPDATE, @Update );
+  // RU: Регистрируем процедуру, которая выполнится после завершения работы ZenGL.
+  // EN: Register the procedure, that will be executed after ZenGL shutdown.
+  zgl_Reg( SYS_EXIT, @Quit );
+
+  // RU: Устанавливаем заголовок окна.
+  // EN: Set the caption of the window.
+  wnd_SetCaption( '01 - Initialization' );
+
+  // RU: Разрешаем курсор мыши.
+  // EN: Allow to show the mouse cursor.
+  wnd_ShowCursor( TRUE );
+
+  // RU: Указываем первоначальные настройки.
+  // EN: Set screen options.
+  zgl_SetParam(800, 600, false, false);
+
+  // RU: Инициализируем ZenGL.
+  // EN: Initialize ZenGL.
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/01 - Initialization/demo01_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo01</string>
+  <key>CFBundleIconFile</key>
+  <string>demo01</string>
+  <key>CFBundleName</key>
+  <string>demo01</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo01</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 0 - 0
Zengl_SRC/demos/FreePascal/01 - Initialization/fp___.err


+ 0 - 0
Zengl_SRC/demos/FreePascal/01 - Initialization/fp___.out


+ 3 - 0
Zengl_SRC/demos/FreePascal/01 - Initialization/macosx_postbuild.sh

@@ -0,0 +1,3 @@
+# make Info.plist and copy icon
+cp -f demo01_macosx.plist ../../../bin/demo01.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo01.app/Contents/Resources/demo01.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/02 - Resources/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo02.pas
+TARGET  = demo02
+TARGETW = demo02.exe
+TARGETM = demo02
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 154 - 0
Zengl_SRC/demos/FreePascal/02 - Resources/demo02.pas

@@ -0,0 +1,154 @@
+program demo02;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  {$IFDEF UNIX}
+  cthreads,
+  {$ENDIF}
+  Classes,
+
+  {$IFDEF USE_ZENGL_STATIC}
+  zgl_types,
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  // RU: Модули для работы с файлами, файлами в памяти и zip-архивами.
+  // EN: Units for using files, files in memory and zip archives.
+  zgl_file,
+  zgl_memory,
+  // RU: Модуль для поддержки многопоточной загрузки ресурсов.
+  // EN: Unit for multithreaded resource loading.
+  zgl_resources,
+  // RU: Модуль для работы со шрифтами.
+  // EN: Unit for using fonts.
+  zgl_font,
+  // RU: Модули для работы с текстурами. zgl_textures является основным, следующие за ним предоставляют поддержку определённых форматов.
+  // EN: Units for using textures. zgl_textures is a main unit, next units provide support of different formats.
+  zgl_textures,
+  zgl_textures_tga, // TGA
+  zgl_textures_jpg, // JPG
+  zgl_textures_png, // PNG
+  // RU: Звуковая подсистема реализована в модулях ниже. Подход такой же как и с текстурами - основной модуль и модули поддержки форматов.
+  // EN: Sound subsystem implemented in units below. Idea the same as for textures - there is a main unit and units for support different formats.
+  zgl_sound,
+  zgl_sound_wav, // WAV
+  zgl_sound_ogg, // OGG
+
+  zgl_primitives_2d,
+  zgl_text,
+  zgl_sprite_2d,
+  zgl_utils
+  {$ELSE}
+  zglHeader
+  {$ENDIF}
+  ;
+
+var
+  dirRes : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+
+  memory : zglTMemory;
+
+  // RU: У каждого ресурса есть свой определённый тип, который является указателем на структуру.
+  // EN: Every resource has its own typem which is just a pointer to structure.
+  fntMain  : Byte;
+  //
+  texLogo  : zglPTexture;
+  texTest  : zglPTexture;
+  //
+  sndClick : zglPSound;
+  sndMusic : zglPSound;
+
+procedure TextureCalcEffect( pData : PByteArray; Width, Height : Word );
+begin
+  u_Sleep( 1000 );
+end;
+
+procedure Init;
+  var
+    i         : Integer;
+    memStream : TMemoryStream;
+begin
+  // RU: Более детальное рассмотрение параметров функций загрузки ресурсов есть в соответствующих примерах, тут же показана лишь основная суть.
+  // EN: Description with more details about parameters of functions can be found in other demos, here is only main idea shown.
+
+  snd_Init();
+
+  // RU: Функции загрузки ресурсов именуются в формате "$(префикс)_LoadFrom$(откуда)", где "$(префикс)" может быть tex, snd, font и т.д., а "$(откуда)" - File и Memory.
+  // EN: Functions for loading resources named in format "$(prefix)_LoadFrom$(where)", where "$(prefix)" can be tex, snd, font and so on, and $(where) - File and Memory.
+  fntMain  := font_LoadFromFile( dirRes + 'font.zfi' );
+  texLogo  := tex_LoadFromFile( dirRes + 'zengl.png' );
+  sndClick := snd_LoadFromFile( dirRes + 'click.wav' );
+
+  // RU: Многопоточная загрузка ресурсов позволяет составить очередь и не ожидать загрузки выполняя другие операции, например рендеринг какой-то анимации.
+  //     Процесс загрузки в многопоточном режиме практически ничем не отличается от обычного за исключением вызова функций старта и окончания очереди.
+  // EN: Multithreaded resource loading allows to make queue and do something while loading, e.g. rendering some animation.
+  //     Loading resources in multithreaded mode has almost no difference with standard mode, except using functions for beginning and ending queues.
+  res_BeginQueue( 0 );
+  // RU: Между res_BeginQueue и res_EndQueue могут использоваться все обычные функции загрузки ресурсов.
+  //     Для задержки экрана загрузки ресурсы будут загружены несколько раз, а для текстуры будет использована обработка с задержкой.
+  // EN: All standard functions for loading resources can be used between res_BeginQueue and res_EndQueue.
+  //     Just for holding loading screen resources will be loaded multiple times, and texture will be post-processed with delay.
+  zgl_Reg( TEXTURE_CURRENT_EFFECT, @TextureCalcEffect );
+  for i := 0 to 3 do
+    begin
+      texTest  := tex_LoadFromFile( dirRes + 'back01.jpg', TEX_NO_COLORKEY, TEX_DEFAULT_2D or TEX_CUSTOM_EFFECT );
+      sndMusic := snd_LoadFromFile( dirRes + 'music.ogg' );
+    end;
+  res_EndQueue();
+
+  // RU: Загружая ресурсы из файлов в памяти необходимо дополнительно указывать их расширение.
+  //     В качестве примера будет использован TMemoryStream вместо mem_LoadFromFile/mem_Free что бы показать как устроен zglTMemory.
+  // EN: Loading resources from files in memory need additional set their extension.
+  //     As an example TMemoryStream will be used instead of mem_LoadFromFile/mem_Free, just for showing how zglTMemory works.
+  memStream := TMemoryStream.Create();
+  {$IFNDEF MACOSX}
+  memStream.LoadFromFile( dirRes + 'back01.jpg' );
+  {$ELSE}
+  memStream.LoadFromFile( PAnsiChar( zgl_Get( DIRECTORY_APPLICATION ) ) + 'Contents/Resources/back01.jpg' );
+  {$ENDIF}
+  memory.Position := memStream.Position;
+  memory.Memory   := memStream.Memory;
+  memory.Size     := memStream.Size;
+  texTest := tex_LoadFromMemory( memory, 'JPG' );
+  memStream.Free();
+  // код выше с использованием Stream не заработал у меня с MacOS Cocoa
+  //texTest := tex_LoadFromFile(dirRes + 'back01.jpg');
+
+  // RU: Для загрузки ресурсов из zip-архива необходимо его сначала "открыть" и потом "закрыть" :) Для этого существуют функции file_OpenArchive и file_CloseArchive.
+  // EN: For loading resources from zip-archive this archive should be "opened" first and then "closed" :) There are functions file_OpenArchive and file_CloseArchive for this.
+  file_OpenArchive( dirRes + 'zengl.zip' );
+  texLogo := tex_LoadFromFile( 'zengl.png' );
+  file_CloseArchive();
+
+  setTextScale(15, fntMain);
+end;
+
+procedure Draw;
+begin
+  // RU: К ресурсам, которые загружаются в многопоточном режиме, можно обращаться только после завершения загрузки. Код ниже рисует экран загрузки если ресурсы ещё не загрузились.
+  // EN: Resources which are loading in multithreaded mode can be used only after finishing the loading process. Code below renders loading screen if resources are not loaded yet.
+  if res_GetCompleted() < 100 Then
+    begin
+      ssprite2d_Draw( texLogo, ( 800 - texLogo.Width ) / 2, ( 600 - texLogo.Height ) / 2, texLogo.Width, texLogo.Height, 0 );
+      text_Draw( fntMain, 400, 300 + texLogo.Height / 4, 'Loading... ' + u_IntToStr( res_GetCompleted() ) + '%', TEXT_HALIGN_CENTER );
+      exit;
+    end;
+
+  ssprite2d_Draw( texTest, 0, 0, 800, 600, 0 );
+  text_Draw( fntMain, 0, 0, 'FPS: ' + u_IntToStr( zgl_Get( RENDER_FPS ) ) );
+  text_Draw( fntMain, 0, 18, 'VRAM Used: ' + u_FloatToStr( zgl_Get( RENDER_VRAM_USED ) / 1024 / 1024 ) + 'Mb' );
+end;
+
+Begin
+  {$IFNDEF USE_ZENGL_STATIC}
+  if not zglLoad( libZenGL ) Then exit;
+  {$ENDIF}
+
+  zgl_Reg( SYS_LOAD, @Init );
+  zgl_Reg( SYS_DRAW, @Draw );
+
+  wnd_SetCaption(utf8_Copy('02 - Resources'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/02 - Resources/demo02_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo02</string>
+  <key>CFBundleIconFile</key>
+  <string>demo02</string>
+  <key>CFBundleName</key>
+  <string>demo02</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo02</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 10 - 0
Zengl_SRC/demos/FreePascal/02 - Resources/macosx_postbuild.sh

@@ -0,0 +1,10 @@
+# copy resources
+cp ../../../bin/data/font* ../../../bin/demo02.app/Contents/Resources/
+cp ../../../bin/data/zengl.png ../../../bin/demo02.app/Contents/Resources/
+cp ../../../bin/data/click.wav ../../../bin/demo02.app/Contents/Resources/
+cp ../../../bin/data/back01.jpg ../../../bin/demo02.app/Contents/Resources/
+cp ../../../bin/data/music.ogg ../../../bin/demo02.app/Contents/Resources/
+cp ../../../bin/data/zengl.zip ../../../bin/demo02.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo02_macosx.plist ../../../bin/demo02.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo02.app/Contents/Resources/demo02.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/03 - Input/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo03.pas
+TARGET  = demo03
+TARGETW = demo03.exe
+TARGETM = demo03
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 157 - 0
Zengl_SRC/demos/FreePascal/03 - Input/demo03.pas

@@ -0,0 +1,157 @@
+program demo03;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  {$IFDEF UNIX}
+  cthreads,
+  {$ENDIF}
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_mouse,
+  zgl_keyboard,
+  zgl_joystick,
+  zgl_primitives_2d,
+  zgl_font,
+  zgl_text,
+  zgl_textures_png,
+  zgl_types,
+  zgl_collision_2d,
+  zgl_utils
+  ;
+
+var
+  dirRes  : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+
+  fntMain    : Byte;
+
+  joyCount   : Integer;
+  userInput  : UTF8String;
+  trackInput : Boolean;
+  inputRect  : zglTRect;
+  lineAlpha  : Byte;
+
+  TimeStart  : Byte;
+
+procedure Init;
+begin
+  fntMain := font_LoadFromFile( dirRes + 'font.zfi' );
+  setTextScale(15, fntMain);
+
+  inputRect.X := 400 - 192;
+  inputRect.Y := 300 - 100 - 32;
+  inputRect.W := 384;
+  inputRect.H := 96;
+
+  // RU: Инициализируем обработку ввода джойстиков и получаем количество подключенных джойстиков.
+  // EN: Initialize processing joystick input and get count of plugged joysticks.
+  joyCount := joy_Init();
+end;
+
+procedure Draw;
+  var
+    w : Single;
+begin
+  text_Draw( fntMain, 0, 0, 'Escape - Exit' );
+
+  // RU: Координаты мыши можно получить при помощи функций mouse_X и mouse_Y.
+  // EN: Mouse coordinates can be got using functions mouse_X and mouse_Y.
+  text_Draw( fntMain, 0, 18, 'Mouse X, Y: ' + u_IntToStr( mouseX ) + '; ' + u_IntToStr( mouseY ) );
+
+  // RU: Выводим введённый пользователем текст.
+  // EN: Show the inputted text.
+  pr2d_Rect( inputRect.X, inputRect.Y, inputRect.W, inputRect.H, $FFFFFF, 255 );
+  if trackInput Then
+    begin
+      text_Draw( fntMain, 400, 300 - 100, 'Press Enter to stop track text input:', TEXT_HALIGN_CENTER );
+      w := text_GetWidth( fntMain, userInput );
+      pr2d_Rect( 400 + w / 2 + 2, 300 - 70, 10, 20, $FFFFFF, lineAlpha, PR2D_FILL );
+    end else
+      text_Draw( fntMain, 400, 300 - 100, 'Click here to enter text(maximum - 24 symbols):', TEXT_HALIGN_CENTER );
+  text_Draw( fntMain, 400, 300 - 70, userInput, TEXT_HALIGN_CENTER );
+
+
+  // RU: Вывод состояния осей и кнопок первого джойстика в системе.
+  // EN: Show the state of axes and buttons of first joystick in the system.
+  text_Draw( fntMain, 400, 360, 'JOYSTICK ( Found: ' + u_IntToStr( joyCount ) + ' )', TEXT_HALIGN_CENTER );
+
+  text_Draw( fntMain, 100, 400, 'Axis X: ' + u_FloatToStr( joy_AxisPos( 0, JOY_AXIS_X ) ) );
+  text_Draw( fntMain, 100, 420, 'Axis Y: ' + u_FloatToStr( joy_AxisPos( 0, JOY_AXIS_Y ) ) );
+  text_Draw( fntMain, 100, 440, 'Axis Z: ' + u_FloatToStr( joy_AxisPos( 0, JOY_AXIS_Z ) ) );
+  text_Draw( fntMain, 100, 460, 'Axis R: ' + u_FloatToStr( joy_AxisPos( 0, JOY_AXIS_R ) ) );
+  text_Draw( fntMain, 100, 480, 'Axis U: ' + u_FloatToStr( joy_AxisPos( 0, JOY_AXIS_U ) ) );
+  text_Draw( fntMain, 100, 500, 'Axis V: ' + u_FloatToStr( joy_AxisPos( 0, JOY_AXIS_V ) ) );
+  text_Draw( fntMain, 100, 520, 'POVX: ' + u_FloatToStr( joy_AxisPos( 0, JOY_POVX ) ) );
+  text_Draw( fntMain, 100, 540, 'POVY: ' + u_FloatToStr( joy_AxisPos( 0, JOY_POVY ) ) );
+
+  text_Draw( fntMain, 400, 400, 'Button1: ' + u_BoolToStr( joy_Down( 0, 0 ) ) );
+  text_Draw( fntMain, 400, 420, 'Button2: ' + u_BoolToStr( joy_Down( 0, 1 ) ) );
+  text_Draw( fntMain, 400, 440, 'Button3: ' + u_BoolToStr( joy_Down( 0, 2 ) ) );
+  text_Draw( fntMain, 400, 460, 'Button4: ' + u_BoolToStr( joy_Down( 0, 3 ) ) );
+  text_Draw( fntMain, 400, 480, 'Button5: ' + u_BoolToStr( joy_Down( 0, 4 ) ) );
+  text_Draw( fntMain, 400, 500, 'Button6: ' + u_BoolToStr( joy_Down( 0, 5 ) ) );
+  text_Draw( fntMain, 400, 520, 'Button7: ' + u_BoolToStr( joy_Down( 0, 6 ) ) );
+  text_Draw( fntMain, 400, 540, 'Button8: ' + u_BoolToStr( joy_Down( 0, 7 ) ) );
+  text_Draw( fntMain, 550, 400, 'Button9: ' + u_BoolToStr( joy_Down( 0, 8 ) ) );
+  text_Draw( fntMain, 550, 420, 'Button10: ' + u_BoolToStr( joy_Down( 0, 9 ) ) );
+  text_Draw( fntMain, 550, 440, 'Button11: ' + u_BoolToStr( joy_Down( 0, 10 ) ) );
+  text_Draw( fntMain, 550, 460, 'Button12: ' + u_BoolToStr( joy_Down( 0, 11 ) ) );
+  text_Draw( fntMain, 550, 480, 'Button13: ' + u_BoolToStr( joy_Down( 0, 12 ) ) );
+  text_Draw( fntMain, 550, 500, 'Button14: ' + u_BoolToStr( joy_Down( 0, 13 ) ) );
+  text_Draw( fntMain, 550, 520, 'Button15: ' + u_BoolToStr( joy_Down( 0, 14 ) ) );
+  text_Draw( fntMain, 550, 540, 'Button16: ' + u_BoolToStr( joy_Down( 0, 15 ) ) );
+end;
+
+procedure Timer;
+begin
+  if lineAlpha > 5 Then
+    DEC( lineAlpha, 10 )
+  else
+    lineAlpha := 255;
+
+  // RU: Проверить нажата ли левая кнопка мыши в пределах inputRect и начать отслеживать ввод текста.
+  // EN: Check if left mouse button was pressed inside inputRect and start to track text input.
+  if mBClickCanClick( M_BLEFT_CLICK ) and col2d_PointInRect( mouseX, mouseY, inputRect ) Then
+  begin
+    trackInput := TRUE;
+    key_BeginReadText( userInput, 24 );
+  end;
+
+  // RU: Если был нажат Enter прекращаем отслеживать ввод текста.
+  // EN: Finish to track text input if Enter was pressed.
+  if key_Press( K_ENTER ) Then
+  begin
+    trackInput := FALSE;
+    key_EndReadText();
+  end;
+
+  // RU: Получаем введённый пользователем текст.
+  // EN: Get inputted by user text.
+  if trackInput Then
+    userInput := key_GetText();
+
+  // RU: По нажатию Escape завершить приложение.
+  // EN: If Escape was pressed - shutdown the application.
+
+  // if key_Press( K_ESCAPE ) Then zgl_Exit;
+                   // больше не нужно это делать, но если для чего-то понадобится клавиша Escape, надо
+                   // отключить дефайн (USE_EXIT_ESCAPE) на её обработку
+
+  // RU: Обязательно очищаем состояния всех подсистем ввода.
+  // EN: Necessarily clear all the states of input subsystems.
+  mouse_ClearState();
+  key_ClearState();
+  joy_ClearState();
+end;
+
+Begin
+  TimeStart := timer_Add( @Timer, 16, Start );
+
+  zgl_Reg( SYS_LOAD, @Init );
+  zgl_Reg( SYS_DRAW, @Draw );
+
+  wnd_SetCaption(utf8_Copy('03 - Input'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/03 - Input/demo03_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo03</string>
+  <key>CFBundleIconFile</key>
+  <string>demo03</string>
+  <key>CFBundleName</key>
+  <string>demo03</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo03</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 5 - 0
Zengl_SRC/demos/FreePascal/03 - Input/macosx_postbuild.sh

@@ -0,0 +1,5 @@
+# copy resources
+cp ../../../bin/data/font* ../../../bin/demo03.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo03_macosx.plist ../../../bin/demo03.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo03.app/Contents/Resources/demo03.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/04 - Screen Settings/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo04.pas
+TARGET  = demo04
+TARGETW = demo04.exe
+TARGETM = demo04
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 152 - 0
Zengl_SRC/demos/FreePascal/04 - Screen Settings/demo04.pas

@@ -0,0 +1,152 @@
+program demo04;
+
+{$I zglCustomConfig.cfg}
+
+// не рекомендуется к использованию!!! Особенно на MacOS Cocoa! Желательно перезагружать программу,
+// в особенности, если вы делаете полноэкранное окно
+
+// not recomended use in MacOS Cocoa.
+
+uses
+  {$IFDEF UNIX}
+  cthreads,
+  {$ENDIF}
+  {$IFDEF USE_ZENGL_STATIC}
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_font,
+  zgl_text,
+  zgl_sprite_2d,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_textures_jpg,
+  zgl_utils
+  {$ELSE}
+  zglHeader
+  {$ENDIF}
+  ;
+
+var
+  dirRes  : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+
+  fntMain : Byte;
+  texBack : zglPTexture;
+
+  TimeStart  : Byte = 0;
+
+procedure Init;
+begin
+  fntMain := font_LoadFromFile( dirRes + 'font.zfi' );
+  texBack := tex_LoadFromFile( dirRes + 'back03.jpg' );
+
+  setTextScale(15, fntMain);                  // razmery shrifta
+end;
+
+procedure Draw;
+begin
+  ssprite2d_Draw( texBack, 0, 0, 800, 600, 0 );
+
+  text_Draw( fntMain, 0, 0, 'Escape - Exit' );
+  text_Draw( fntMain, 0, 20 * 1, 'F1 - Fullscreen with desktop resolution and correction of aspect' );
+  text_Draw( fntMain, 0, 20 * 2, 'F2 - Fullscreen with desktop resolution and simple scaling' );
+  text_Draw( fntMain, 0, 20 * 3, 'F3 - Fullscreen with resolution 800x600' );
+  text_Draw( fntMain, 0, 20 * 4, 'F4 - Windowed mode' );
+end;
+
+procedure Timer;
+begin
+  // RU: Рекомендуемый к использованию полноэкранный режим. Основная идея - переключиться в полноэкранный режим используя текущее разрешение рабочего стола пользователя, но при этом
+  //     сохранить пропорции изображения. Это позволит избежать некоторых проблем с LCD.
+  // EN: Recommended fullscreen mode for using. Main idea is switching to fullscreen mode using current desktop resolution of user and saving the aspect. This will avoid some problems
+  //     with LCD's.
+  if key_Press( K_F1 ) Then
+    begin
+      // RU: Включить коррекцию пропорций.
+      // EN: Enable aspect correction.
+      zgl_Enable( CORRECT_RESOLUTION );
+      // RU: Установить разрешение под которое изначально написано приложение.
+      // EN: Set resolution for what application was wrote.
+      scr_CorrectResolution( 800, 600 );
+      zgl_SetParam(zgl_Get( DESKTOP_WIDTH ), zgl_Get( DESKTOP_HEIGHT ), True, False);
+(*  --------------------- OR!!! ----------------------------------------
+      wndWidth := zgl_Get( DESKTOP_WIDTH );
+      wndHeight := zgl_Get( DESKTOP_HEIGHT );
+      wndFullScreen := True;
+      scrVSync := False;
+    -------------------------------------------------------------------- *)
+      scr_SetOptions();
+    end;
+
+  // RU: Схожий режим с предыдущим за одним исключением - отключена коррекция по ширине и высоте. Например, отключение коррекции по высоте может пригодиться при соотошении
+  //     сторон 5:4(разрешение экрана 1280x1024), т.к. можно заполнить всю область экрана без существенных искажений.
+  // EN: Similar mode to previous one with one exception - disabled correction for width and height. E.g. this can be useful for aspect 5:4(resolution 1280x1024),
+  //     because screen can be filled without significant distortion.
+  if key_Press( K_F2 ) Then
+    begin
+      zgl_Enable( CORRECT_RESOLUTION );
+      zgl_Disable( CORRECT_WIDTH or CORRECT_HEIGHT );
+      scr_CorrectResolution( 800, 600 );
+      zgl_SetParam(zgl_Get( DESKTOP_WIDTH ), zgl_Get( DESKTOP_HEIGHT ), True, False);
+(*  --------------------- OR!!! ----------------------------------------
+      wndWidth := zgl_Get( DESKTOP_WIDTH );
+      wndHeight := zgl_Get( DESKTOP_HEIGHT );
+      wndFullScreen := True;
+      scrVSync := False;
+    -------------------------------------------------------------------- *)
+      scr_SetOptions();
+    end;
+
+  // RU: Переключение в полноэкранный режим используя указанные размеры. В наше время такой подход имеет два больших недостатка на LCD:
+  //     - если указываемое разрешение не является родным для LCD, то без специальных настройках в драйверах пользователь будет наблюдать пикселизацию
+  //     - на широкоэкранных мониторах картинка с соотношением 4:3 будет смотрется растянутой
+  // EN: Switching to fullscreen mode using set values. Nowadays this method two main problems with LCD:
+  //     - if used resolution is not main for LCD, then without special options in drivers user will see pixelization
+  //     - picture with aspect 4:3 will be stretched on widescreen monitors
+    if key_Press( K_F3 ) Then
+    begin
+      zgl_Disable( CORRECT_RESOLUTION );
+      zgl_SetParam(800, 600, True, False);
+(* ---------------------- OR!!! ----------------------------------------
+      wndWidth := 800;
+      wndHeight := 600;
+      wndFullScreen := True;
+      scrVSync := False;
+      scr_SetOptions();
+    -------------------------------------------------------------------- *)
+      scr_SetOptions();
+    end;
+
+  // RU: Оконный режим.
+  // EN: Windowed mode.
+  if key_Press( K_F4 ) Then
+    begin
+      zgl_Disable(CORRECT_RESOLUTION);
+      zgl_SetParam(800, 600, False, False);
+(* ---------------------- OR!!! ----------------------------------------
+      wndWidth := 800;
+      wndHeight := 600;
+      wndFullScreen := False;
+      scrVSync := False;
+   -------------------------------------------------------------------- *)
+      scr_SetOptions();
+    end;
+
+  key_ClearState();
+end;
+
+Begin
+  {$IFNDEF USE_ZENGL_STATIC}
+  if not zglLoad( libZenGL ) Then exit;
+  {$ENDIF}
+
+  TimeStart := timer_Add( @Timer, 16, Start );
+
+  zgl_Reg( SYS_LOAD, @Init );
+  zgl_Reg( SYS_DRAW, @Draw );
+
+  wnd_SetCaption(utf8_Copy('04 - Screen Settings'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/04 - Screen Settings/demo04_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo04</string>
+  <key>CFBundleIconFile</key>
+  <string>demo04</string>
+  <key>CFBundleName</key>
+  <string>demo04</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo04</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 6 - 0
Zengl_SRC/demos/FreePascal/04 - Screen Settings/macosx_postbuild.sh

@@ -0,0 +1,6 @@
+# copy resources
+cp ../../../bin/data/font* ../../../bin/demo04.app/Contents/Resources/
+cp ../../../bin/data/back03.jpg ../../../bin/demo04.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo04_macosx.plist ../../../bin/demo04.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo04.app/Contents/Resources/demo04.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/05 - Primitives/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo05.pas
+TARGET  = demo05
+TARGETW = demo05.exe
+TARGETM = demo05
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 91 - 0
Zengl_SRC/demos/FreePascal/05 - Primitives/demo05.pas

@@ -0,0 +1,91 @@
+program demo05;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  {$IFDEF UNIX}
+  cthreads,
+  {$ENDIF}
+  {$IfDef USE_ZENGL_STATIC}
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_fx,
+  zgl_render_2d,
+  zgl_primitives_2d,
+  zgl_types,
+  zgl_math_2d,
+  zgl_utils
+  {$Else}
+  zglHeader
+  {$EndIf}
+  ;
+
+var
+  calc   : Integer;
+  points : array[ 0..359 ] of zglTPoint2D;
+  TimeStart  : Byte = 0;
+
+procedure Init;
+  var
+    i : Integer;
+begin
+  for i := 0 to 359 do
+    begin
+      points[ i ].X := 400 + m_Cos( i ) * ( 96 + random( 32 ) );
+      points[ i ].Y := 300 + m_Sin( i ) * ( 96 + random( 32 ) );
+    end;
+end;
+
+procedure Draw;
+  var
+    i : Integer;
+begin
+  // RU: Устанавливаем цвет и альфу для каждой вершины.
+  // EN: Set color and alpha for each vertex.
+  fx2d_SetVCA( $FF0000, $00FF00, $0000FF, $FFFFFF, 255, 255, 255, 255 );
+  // RU: Рисуем прямоугольник с заливкой(флаг PR2D_FILL) с использованием отдельных цветов для каждой вершины(флаг FX2D_VCA).
+  // EN: Render filled rectangle(flag PR2D_FILL) and use different colors for each vertex(flag FX2D_VCA).
+  pr2d_Rect( 0, 0, 800, 600, $000000, 255, FX2D_VCA or PR2D_FILL );
+
+  // RU: Рисуем в центре экрана круг с радиусом 128 пиксела.
+  // EN: Render circle in the center of screen with radius 128 pixels.
+  pr2d_Circle( 400, 300, 128, $000000, 155, 32, PR2D_FILL );
+
+  INC( calc );
+  if calc > 359 Then calc := 0;
+  points[ calc ].X := 400 + m_Cos( calc ) * ( 96 + random( 32 ) );
+  points[ calc ].Y := 300 + m_Sin( calc ) * ( 96 + random( 32 ) );
+  // RU: Рисуем линии внутри круга.
+  // EN: Render lines inside the circle.
+  for i := 0 to 359 do
+    pr2d_Line( 400, 300, points[ i ].X, points[ i ].Y, $FFFFFF, 255 );
+
+  // RU: Рисуем эллипсы с заливкой и без, со сглаженными контурами(флаг PR2D_SMOOTH).
+  // EN: Render filled ellipses with smoothed edges(flag PR2D_SMOOTH).
+  pr2d_Ellipse( 400 + 300, 300, 64, 256, $FFFFFF, 55, 32, PR2D_FILL or PR2D_SMOOTH );
+  pr2d_Ellipse( 400 + 300, 300, 64, 256, $000000, 255, 32, PR2D_SMOOTH );
+
+  pr2d_Ellipse( 400 - 300, 300, 64, 256, $FFFFFF, 55, 32, PR2D_FILL or PR2D_SMOOTH );
+  pr2d_Ellipse( 400 - 300, 300, 64, 256, $000000, 255, 32, PR2D_SMOOTH );
+end;
+
+procedure Timer;
+begin
+  key_ClearState();
+end;
+
+Begin
+  {$IFNDEF USE_ZENGL_STATIC}
+  if not zglLoad( libZenGL ) Then exit;
+  {$ENDIF}
+  TimeStart := timer_Add( @Timer, 16, Start );
+
+  zgl_Reg( SYS_LOAD, @Init );
+  zgl_Reg( SYS_DRAW, @Draw );
+
+  wnd_SetCaption(utf8_Copy('05 - Primitives'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/05 - Primitives/demo05_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo05</string>
+  <key>CFBundleIconFile</key>
+  <string>demo05</string>
+  <key>CFBundleName</key>
+  <string>demo05</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo05</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 3 - 0
Zengl_SRC/demos/FreePascal/05 - Primitives/macosx_postbuild.sh

@@ -0,0 +1,3 @@
+# make Info.plist and copy icon
+cp -f demo05_macosx.plist ../../../bin/demo05.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo05.app/Contents/Resources/demo05.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/06 - Text/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo06.pas
+TARGET  = demo06
+TARGETW = demo06.exe
+TARGETM = demo06
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 129 - 0
Zengl_SRC/demos/FreePascal/06 - Text/demo06.pas

@@ -0,0 +1,129 @@
+program demo06;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  {$IF defined(LINUX) or defined (MACOSX)}
+  cthreads,
+  {$IfEnd}
+  {$IFDEF USE_ZENGL_STATIC}
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_render_2d,
+  zgl_fx,
+  zgl_primitives_2d,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_font,
+  zgl_text,
+  zgl_file,
+  zgl_types,
+  zgl_utils
+  {$ELSE}
+  zglHeader
+  {$ENDIF}
+  ;
+
+var
+//  dirRes  : UTF8String {$IFNDEF MACOSX} = 'data/' {$ENDIF};             // вне демо-версий
+  dirRes  : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};            // в демо-версиях!!!
+  fntMain : Byte;
+
+  TimeStart  : Byte = 0;
+
+procedure Init;
+begin
+//  file_SetPath('');                       // если dirRes = '../data/'   !!!!!     в демо-версиях!!!
+  // RU: Загружаем данные о шрифте.
+  // EN: Load the font.
+
+  fntMain := font_LoadFromFile( dirRes + 'font.zfi' );
+  // RU: Если же текстуры именуются без использования маски вида "$(имя_шрифта)FontName-page$(номер).$(расширение)", то загрузку можно произвести следующим образом(для png):
+  // EN: If textures were named without special mask - "$(font_name)-page$(number).$(extension)", then use this method to load them(for png):
+  //for i := 0 to fntMain.Count.Pages - 1 do
+  //  fntMain.Pages[ i ] := tex_LoadFromFile( dirRes + 'font-page' + u_IntToStr( i ) + '.png' );
+end;
+
+procedure Draw;
+  var
+    r : zglTRect;
+    s : UTF8String;
+begin
+  batch2d_Begin();
+//  setTextScale(1.5, fntMain);
+
+  // RU: ZenGL работает исключительно с кодировкой UTF-8, поэтому весь текст должен быть в UTF-8.
+  // EN: ZenGL works only with UTF-8 encoding, so all text should be encoded with UTF-8.
+
+  text_Draw( fntMain, 400, 25, 'String with center alignment', TEXT_HALIGN_CENTER );
+
+  text_DrawEx( fntMain, 400, 65, 3, 0, 'Scaling', 255, $FFFFFF, TEXT_HALIGN_CENTER );
+
+  setTextScale(15, fntMain);
+  fx2d_SetVCA( $FF0000, $00FF00, $0000FF, $FFFFFF, 255, 255, 255, 255 );
+  text_Draw( fntMain, 400, 125, 'Gradient color for every symbol', TEXT_FX_VCA or TEXT_HALIGN_CENTER );
+
+  r.X := 0;
+  r.Y := 300 - 128;
+  r.W := 192;
+  r.H := 256;
+
+  pr2d_Rect( r.X, r.Y, r.W, r.H, $FF0000 );
+  text_DrawInRect( fntMain, r, 'Simple text rendering in rectangle' + #10 + 'Текст написанный в квадрате');
+  // для использования другой кодировки надо указать Lazarus что страница в кодировке UTF-8 BOM!!!
+  // File setting -> encoding -> UTF-8 with BOM
+
+  r.X := 800 - 192;
+  r.Y := 300 - 128;
+  r.W := 192;
+  r.H := 256;
+  pr2d_Rect( r.X, r.Y, r.W, r.H, $FF0000 );
+  text_DrawInRect( fntMain, r, 'Text rendering using horizontal right alignment and vertical bottom alignment', TEXT_HALIGN_RIGHT or TEXT_VALIGN_BOTTOM );
+
+  r.X := 400 - 192;
+  r.Y := 300 - 128;
+  r.W := 384;
+  r.H := 256;
+  pr2d_Rect( r.X, r.Y, r.W, r.H, $FF0000 );
+  text_DrawInRect( fntMain, r, 'This text uses justify alignment and centered vertically. Text which doesn''t fit inside the rectangle will be cropped.',
+                   TEXT_HALIGN_JUSTIFY or TEXT_VALIGN_CENTER );
+
+  r.X := 400 - 320;
+  r.Y := 300 + 160;
+  r.W := 640;
+  r.H := 128;
+  pr2d_Rect( r.X, r.Y, r.W, r.H, $FF0000 );
+  text_DrawInRect( fntMain, r, 'For starting new line LF symbol can be used' + #10 + 'code of which is equal to 10 and named in Unicode as "Line Feed"',
+                   TEXT_HALIGN_CENTER or TEXT_VALIGN_CENTER );
+
+  // RU: Выводим количество FPS в правом углу, используя text_GetWidth.
+  // EN: Render FPS in the top right corner using text_GetWidth.
+  s := 'FPS: ' + u_IntToStr( zgl_Get( RENDER_FPS ) );
+  text_Draw( fntMain, 800 - text_GetWidth( fntMain, s ), 0, s );
+
+  batch2d_End();
+end;
+
+procedure Timer;
+begin
+
+  key_ClearState();
+end;
+
+Begin
+  {$IFNDEF USE_ZENGL_STATIC}
+  if not zglLoad( libZenGL ) Then exit;
+  {$ENDIF}
+  randomize();
+
+  timer_Add( @Timer, 16, TimeStart, Start );
+
+  zgl_Reg( SYS_LOAD, @Init );
+  zgl_Reg( SYS_DRAW, @Draw );
+
+  wnd_SetCaption(utf8_Copy('06 - Text'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/06 - Text/demo06_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo06</string>
+  <key>CFBundleIconFile</key>
+  <string>demo06</string>
+  <key>CFBundleName</key>
+  <string>demo06</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo06</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 5 - 0
Zengl_SRC/demos/FreePascal/06 - Text/macosx_postbuild.sh

@@ -0,0 +1,5 @@
+# copy resources
+cp ../../../bin/data/font* ../../../bin/demo06.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo06_macosx.plist ../../../bin/demo06.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo06.app/Contents/Resources/demo06.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/07 - Sprites/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo07.pas
+TARGET  = demo07
+TARGETW = demo07.exe
+TARGETM = demo07
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 256 - 0
Zengl_SRC/demos/FreePascal/07 - Sprites/demo07.pas

@@ -0,0 +1,256 @@
+program demo07;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_camera_2d,
+  zgl_render_2d,
+  zgl_fx,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_textures_jpg,
+  zgl_sprite_2d,
+  zgl_primitives_2d,
+  zgl_font,
+  zgl_text,
+  zgl_types,
+  zgl_utils;
+
+type
+  TTux = record
+    Texture : zglPTexture;
+    Frame   : Integer;
+    Pos     : zglTPoint2D;
+end;
+
+var
+  dirRes      : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};    // äèðåêòîðèÿ ðåñóðñîâ
+  fntMain     : Byte;                                             // ýòî ôîíò
+  texLogo     : zglPTexture;
+  texBack     : zglPTexture;
+  texGround   : zglPTexture;
+  texTuxWalk  : zglPTexture;
+  texTuxStand : zglPTexture;
+  tux         : array[0..20] of TTux;
+  time        : Integer;
+  camMain     : zglTCamera2D;
+
+  TimeStart: Byte;
+procedure Init;
+  var
+    i : Integer;
+begin
+  // RU: Ò.ê. ïî óìîë÷àíèþ âñÿ ñòðóêòóðà êàìåðû çàïîëíÿåòñÿ íóëÿìè, ñëåäóåò èíèöèàëèçèðîâàòü å¸ ñòàíäàðòíûìè çíà÷åíèÿìè.
+  // EN: Camera must be initialized, because camera structure is zero-filled by default.
+  cam2d_Init(camMain);
+
+  // RU: Çàãðóæàåì òåêñòóðó.
+  //     $FF000000 - óêàçûâàåò íà òî, ÷òî áû èñïîëüçîâàòü àëüôà-êàíàë èç èçîáðàæåíèÿ.
+  //     TEX_DEFAULT_2D - êîìïëåêñ ôëàãîâ, íåîáõîäèìûõ äëÿ 2D-ñïðàéòîâ. Îïèñàíèå åñòü â ñïðàâêå.
+  // EN: Load the texture.
+  //     $FF000000 - means that alpha channel must be used from file, without colorkey.
+  //     TEX_DEFAULT_2D - complex of flags that needed for 2D sprites. Description can be found in help.
+  texLogo := tex_LoadFromFile(dirRes + 'zengl.png', $FF000000, TEX_DEFAULT_2D);
+
+  texBack := tex_LoadFromFile(dirRes + 'back01.jpg');
+
+  texGround := tex_LoadFromFile(dirRes + 'ground.png');
+  // RU: Óêàçûâàåì ðàçìåð êàäðà â òåêñòóðå.
+  // EN: Set the size of single frame for texture.
+  tex_SetFrameSize(texGround, 32, 32);
+
+  texTuxWalk := tex_LoadFromFile(dirRes + 'tux_walking.png');
+  tex_SetFrameSize(texTuxWalk, 64, 64);
+  texTuxStand := tex_LoadFromFile(dirRes + 'tux_stand.png');
+  tex_SetFrameSize(texTuxStand, 64, 64);
+
+  for i := 0 to 9 do
+  begin
+    tux[i].Texture := texTuxWalk;
+    tux[i].Frame   := random(19) + 2;
+    tux[i].Pos.X   := i * 96;
+    tux[i].Pos.Y   := 32;
+  end;
+  for i := 10 to 19 do
+  begin
+    tux[i].Texture := texTuxWalk;
+    tux[i].Frame   := random(19) + 2;
+    tux[i].Pos.X   := (i - 9) * 96;
+    tux[i].Pos.Y   := 600 - 96;
+  end;
+  tux[20].Texture := texTuxStand;
+  tux[20].Frame   := random(19) + 2;
+  tux[20].Pos.X   := 400 - 32;
+  tux[20].Pos.Y   := 300 - 64 - 4;
+
+  // RU: Çàãðóæàåì øðèôò.
+  // EN: Load the font.
+  fntMain := font_LoadFromFile(dirRes + 'font.zfi');
+  setTextScale(15, fntMain);
+end;
+
+procedure Draw;
+var
+  i : Integer;
+  t : Single;
+  ScaleF: LongWord;
+begin
+//  batch2d_Begin();          // íå ðåêîìåíäóåòñÿ äëÿ ÏÊ    not reccomended for PC
+                              // use for Android and iOS
+  ScaleF := 15;
+  if time > 255 Then
+  begin
+      // RU: Äëÿ óâåëè÷åíèÿ áûñòðîäåéñòâèÿ ìîæíî îòêëþ÷èòü î÷èñòêó áóôåðà öâåòà, ó÷èòûâàÿ ÷òî ýêðàí ïîëíîñòüþ çàïîëíåí.
+      // EN: Rendering perfomance can be increased by disabling clearing the color buffer. This is a good idea because screen is full of objects.
+    zgl_Disable(COLOR_BUFFER_CLEAR);
+
+      // RU: Ðèñóåì çàäíèé ôîí ñ ðàçìåðàìè 800õ600 èñïîëüçóÿ òåêñòóðó back.
+      // EN: Render the background with size 800x600 and using texture "back".
+    ssprite2d_Draw(texBack, 0, 0, 800, 600, 0);
+
+      // RU: Óñòàíîâèòü òåêóùóþ êàìåðó.
+      // EN: Set the current camera.
+    cam2d_Set(@camMain);
+
+      // RU: Ðèñóåì çåìëþ.
+      // EN: Render the ground.
+    for i := - 2 to 800 div 32 + 1 do
+      asprite2d_Draw(texGround, i * 32, 96 - 12, 32, 32, 0, 2);
+    for i := - 2 to 800 div 32 + 1 do
+      asprite2d_Draw(texGround, i * 32, 600 - 32 - 12, 32, 32, 0, 2);
+
+      // RU: Ðèñóåì øàãàþùèõ ïèíãâèíîâ.
+      // EN: Render penguins
+    for i := 0 to 9 do
+      if i = 2 Then
+      begin
+            // RU: Ðèñóåì íàäïèñü â "ðàìî÷êå" íàä ïèíãâèíîì.
+            // EN: Render the text in frame over penguins.
+        t := text_GetWidth( fntMain, 'I''m so red...' ) * 0.75;
+        pr2d_Rect(tux[i].Pos.X - 1, tux[i].Pos.Y - ScaleF + 4, t, ScaleF, $000000, 200, PR2D_FILL);
+        pr2d_Rect(tux[i].Pos.X - 2, tux[i].Pos.Y - ScaleF + 3, t + 2, ScaleF + 2, $FFFFFF);
+        text_DrawEx(fntMain, tux[i].Pos.X, tux[i].Pos.Y - ScaleF + 5, 1, 0, 'I''m so red...');
+            // RU: Ðèñóåì êðàñíîãî ïèíãâèíà èñïîëüçóÿ fx2d-ôóíêöèþ è ôëàã FX_COLOR.
+            // EN: Render red penguin using fx2d-function and flag FX_COLOR.
+        fx2d_SetColor($FF0000);
+        asprite2d_Draw(tux[i].Texture, tux[i].Pos.X, tux[i].Pos.Y, 64, 64, 0, tux[i].Frame div 2, 255, FX_BLEND or FX_COLOR);
+      end else
+      if i = 7 Then
+      begin
+        t := text_GetWidth(fntMain, '???') * 0.75;
+        pr2d_Rect(tux[i].Pos.X + 32 - t / 2, tux[i].Pos.Y - ScaleF + 4, t, ScaleF, $000000, 200, PR2D_FILL);
+        pr2d_Rect(tux[i].Pos.X + 32 - t / 2 - 1, tux[i].Pos.Y - ScaleF + 3, t + 2, ScaleF + 2, $FFFFFF);
+        text_DrawEx(fntMain, tux[i].Pos.X + 32, tux[i].Pos.Y - ScaleF + 5, 1, 0, '???', 255, $FFFFFF, TEXT_HALIGN_CENTER);
+                // RU: Ðèñóåì ïèíãâèíà ïðèâåäåíèå èñïîëüçóÿ ôëàã FX_COLOR óñòàíîâèâ ðåæèì â FX_COLOR_SET :)
+                // EN: Render penguin ghost using flag FX_COLOR and mode FX_COLOR_SET :)
+        fx_SetColorMode(FX_COLOR_SET);
+        fx2d_SetColor($FFFFFF);
+        asprite2d_Draw(tux[i].Texture, tux[i].Pos.X, tux[i].Pos.Y, 64, 64, 0, tux[i].Frame div 2, 155, FX_BLEND or FX_COLOR);
+                // RU: Âîçâðàùàåì îáû÷íûé ðåæèì.
+                // EN: Return default mode.
+        fx_SetColorMode(FX_COLOR_MIX);
+      end else
+        asprite2d_Draw(tux[i].Texture, tux[i].Pos.X, tux[i].Pos.Y, 64, 64, 0, tux[i].Frame div 2);
+
+      // RU: Ðèñóåì ïèíãâèíîâ øàãàþùèõ â îáðàòíóþ ñòîðîíó èñïîëüçóÿ ôëàã îòðàæåíèÿ òåêñòóðû FX2D_FLIPX.
+      // EN: Render penguins, that go another way using special flag for flipping texture - FX2D_FLIPX.
+    for i := 10 to 19 do
+      if i = 13 Then
+      begin
+        t := text_GetWidth(fntMain, 'I''m so big...') * 0.75;
+        pr2d_Rect(tux[i].Pos.X - 2, tux[i].Pos.Y - ScaleF - 10, t, ScaleF, $000000, 200, PR2D_FILL);
+        pr2d_Rect(tux[i].Pos.X - 3, tux[i].Pos.Y - ScaleF - 11, t + 2, ScaleF + 2, $FFFFFF);
+        text_DrawEx(fntMain, tux[i].Pos.X, tux[i].Pos.Y - ScaleF - 9, 1, 0, 'I''m so big...');
+            // RU: Ðèñóåì "áîëüøåãî" ïèíãâèíà. Ò.ê. FX2D_SCALE óâåëè÷èâàåò ñïðàéò îòíîñèòåëüíî öåíòðà, òî ïèíãâèíà ñëåäóåò íåìíîãî "ïîäíÿòü".
+            // EN: Render "big" penguin. It must be shifted up, because FX2D_SCALE scale sprite relative to the center.
+        fx2d_SetScale(1.25, 1.25);
+        asprite2d_Draw(tux[i].Texture, tux[i].Pos.X, tux[i].Pos.Y - 8, 64, 64, 0, tux[i].Frame div 2, 255, FX_BLEND or FX2D_FLIPX or FX2D_SCALE);
+      end else
+      if i = 17 Then
+      begin
+                // RU: Ðèñóåì "âûñîêîãî" ïèíãâèíà èñïîëüçóÿ âìåñòî ôëàãà FX2D_SCALE ôëàã FX2D_VCHANGE è ôóíêöèþ fx2d_SetVertexes äëÿ ñìåùåíèÿ êîîðäèíàò äâóõ âåðõíèõ âåðøèí ñïðàéòà.
+                // EN: Render "tall" penguin using flag FX2D_VCHANGE instead of FX2D_SCALE, and function fx2d_SetVertexes for shifting upper vertexes of sprite.
+        fx2d_SetVertexes(0, -16, 0, -16, 0, 0, 0, 0);
+        asprite2d_Draw(tux[i].Texture, tux[i].Pos.X, tux[i].Pos.Y, 64, 64, 0, tux[i].Frame div 2, 255, FX_BLEND or FX2D_FLIPX or FX2D_VCHANGE);
+      end else
+        asprite2d_Draw(tux[i].Texture, tux[i].Pos.X, tux[i].Pos.Y, 64, 64, 0, tux[i].Frame div 2, 255, FX_BLEND or FX2D_FLIPX);
+
+      // RU: Ñáðîñèòü êàìåðó.
+      // EN: Reset the camera.
+    cam2d_Set(nil);
+
+      // RU: Ðèñóåì ó÷àñòîê çåìëè ïî öåíòðó ýêðàíà.
+      // EN: Render piece of ground in the center of screen.
+    asprite2d_Draw(texGround, 11 * 32, 300 - 16, 32, 32, 0, 1);
+    asprite2d_Draw(texGround, 12 * 32, 300 - 16, 32, 32, 0, 2);
+    asprite2d_Draw(texGround, 13 * 32, 300 - 16, 32, 32, 0, 3);
+
+    t := text_GetWidth(fntMain, 'o_O') * 0.75;
+    pr2d_Rect(tux[20].Pos.X + 32 - t / 2 - 1, tux[20 ].Pos.Y - ScaleF + 3, t + 2, ScaleF + 2, $000000, 200, PR2D_FILL);
+    pr2d_Rect(tux[20].Pos.X + 32 - t / 2 - 2, tux[20 ].Pos.Y - ScaleF + 2, t + 4, ScaleF + 4, $FFFFFF);
+    text_DrawEx(fntMain, tux[20].Pos.X + 32, tux[20].Pos.Y - ScaleF + 5, 1, 0, 'o_O', 255, $FFFFFF, TEXT_HALIGN_CENTER);
+    asprite2d_Draw(tux[20].Texture, tux[20].Pos.X, tux[20].Pos.Y, 64, 64, 0, tux[20].Frame div 2);
+  end;
+
+  if time <= 255 Then
+    ssprite2d_Draw(texLogo, 400 - 256, 300 - 128, 512, 256, 0, time)
+  else
+  if time < 510 Then
+  begin
+    pr2d_Rect(0, 0, 800, 600, $000000, 510 - time, PR2D_FILL);
+    ssprite2d_Draw(texLogo, 400 - 256, 300 - 128, 512, 256, 0, 510 - time);
+  end;
+
+  if time > 255 Then
+    text_Draw(fntMain, 0, 0, 'FPS: ' + u_IntToStr(zgl_Get(RENDER_FPS)));
+
+//  batch2d_End();                // íå ðåêîìåíäóåòñÿ äëÿ ÏÊ    not reccomended for PC
+                                  // use for Android and iOS
+end;
+
+procedure Timer;
+  var
+    i : Integer;
+begin
+  INC(time, 2);
+
+  camMain.Angle := camMain.Angle + cos(time / 1000) / 10;
+
+  for i := 0 to 20 do                       // êàäðû
+    begin
+      INC(tux[i].Frame );
+      if tux[i].Frame > 20 Then
+        tux[i].Frame := 2;
+    end;
+  for i := 0 to 9 do                        // ñìåùåíèå â îäíó ñòîðîíó
+    begin
+      tux[i].Pos.X := tux[i].Pos.X + 1.5;
+      if tux[i].Pos.X > 864 Then
+        tux[i].Pos.X := - 96;
+    end;
+  for i := 10 to 19 do                      // ñìåùåíèå â äðóãóþ ñòîðîíó
+    begin
+      tux[i].Pos.X := tux[i].Pos.X - 1.5;
+      if tux[i].Pos.X < - 96 Then
+        tux[i].Pos.X := 864;
+    end;
+
+  key_ClearState();
+end;
+
+Begin
+  randomize();
+
+  TimeStart := timer_Add(@Timer, 16, Start);
+
+  zgl_Reg(SYS_LOAD, @Init);
+  zgl_Reg(SYS_DRAW, @Draw );
+
+  wnd_SetCaption(utf8_Copy('07 - Sprites'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/07 - Sprites/demo07_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo07</string>
+  <key>CFBundleIconFile</key>
+  <string>demo07</string>
+  <key>CFBundleName</key>
+  <string>demo07</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo07</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 10 - 0
Zengl_SRC/demos/FreePascal/07 - Sprites/macosx_postbuild.sh

@@ -0,0 +1,10 @@
+# copy resources
+cp ../../../bin/data/zengl.png ../../../bin/demo07.app/Contents/Resources/
+cp ../../../bin/data/back01.jpg ../../../bin/demo07.app/Contents/Resources/
+cp ../../../bin/data/ground.png ../../../bin/demo07.app/Contents/Resources/
+cp ../../../bin/data/tux_walking.png ../../../bin/demo07.app/Contents/Resources/
+cp ../../../bin/data/tux_stand.png ../../../bin/demo07.app/Contents/Resources/
+cp ../../../bin/data/font* ../../../bin/demo07.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo07_macosx.plist ../../../bin/demo07.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo07.app/Contents/Resources/demo07.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/08 - Sprite Engine/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo08.pas
+TARGET  = demo08
+TARGETW = demo08.exe
+TARGETM = demo08
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 202 - 0
Zengl_SRC/demos/FreePascal/08 - Sprite Engine/demo08.pas

@@ -0,0 +1,202 @@
+program demo08;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_render_2d,
+  zgl_fx,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_sprite_2d,
+  zgl_sengine_2d,
+  zgl_primitives_2d,
+  zgl_font,
+  zgl_text,
+  zgl_types,
+  zgl_utils
+  ;
+
+type
+  zglPMikuSprite = ^zglTMikuSprite;
+  zglTMikuSprite = record
+    // RU: Îáÿçàòåëüíàÿ ÷àñòü íîâîãî òèïà ñïðàéòà.
+    // EN: New type should start with this.
+    Sprite: zglTSprite2D;
+
+    // RU: Íîâûå ïàðàìåòðû.
+    // EN: New params.
+    Speed : zglTPoint2D;
+  end;
+
+var
+  dirRes   : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+  fntMain  : Byte;
+  texLogo  : zglPTexture;
+  texMiku  : zglPTexture;
+  time     : Integer;
+  sengine2d: zglTSEngine2D;
+  TimeStart: Byte;
+  TimeMiku : Byte;
+
+// Miku
+procedure MikuInit(var Miku: zglTMikuSprite);
+begin
+  with Miku, Miku.Sprite do
+    begin
+      X := 800 + random(800);
+      Y := random(600 - 128);
+
+      // RU: Çàäàåì ñêîðîñòü äâèæåíèÿ.  Íî ýòî âîîáùå áðåä, åñëè ìû äåëàåì óïðàâëÿåìîãî ïåðñîíàæà
+      // EN: Set the moving speed.
+      Speed.X := - random(10) / 5 - 0.5;
+      Speed.Y := (random(10) - 5) / 5;
+    end;
+end;
+
+procedure MikuDraw(var Miku: zglTMikuSprite);
+begin
+  with Miku.Sprite do
+    asprite2d_Draw(Texture, X, Y, W, H, Angle, Round(Frame), Alpha, FxFlags);
+end;
+
+procedure MikuProc(var Miku: zglTMikuSprite);
+begin
+  with Miku, Miku.Sprite do
+    begin
+      X := X + Speed.X;
+      Y := Y + Speed.Y;
+      Frame := Frame + (abs(speed.X) + abs(speed.Y)) / 25;
+      if Frame > 8 Then
+        Frame := 1;
+
+      // RU: Åñëè ñïðàéò âûõîäèò çà ïðåäåëû ïî X, ñðàçó æå óäàëÿåì åãî.
+      // EN: Delete the sprite if it goes beyond X.
+      if X < -128 Then sengine2d_DelSprite(ID);
+
+      // RU: Åñëè ñïðàéò âûõîäèò çà ïðåäåëû ïî Y, ñòàâèì åãî â î÷åðåäü íà óäàëåíèå.
+      // EN: Add sprite to queue for delete if it goes beyond Y.
+      if Y < -128 Then Destroy := TRUE;
+      if Y > 600  Then Destroy := TRUE;
+    end;
+end;
+
+procedure MikuFree(var Miku: zglTMikuSprite);
+begin
+end;
+
+// RU: Äîáàâèòü 100 ñïðàéòîâ.
+// EN: Add 100 sprites.
+procedure AddMiku;
+  var
+    i: Integer;
+begin
+  // RU: Ïðè äîáàâëåíèè ñïðàéòà â ìåíåäæåð ñïðàéòîâ óêàçûâàåòñÿ òåêñòóðà, ñëîé(ïîëîæåíèå ïî Z) è óêàçàòåëè íà îñíîâíûå ôóíêöèè - Èíèöèàëèçàöèÿ, Ðåíäåð, Îáðàáîòêà è Óíè÷òîæåíèå.
+  // EN: For adding sprite to sprite engine must be set next parameters: texture, layer(Z-coordinate) and pointers to Initialization, Render, Process and Destroy functions.
+  for i := 1 to 100 do
+    sengine2d_AddCustom(texMiku, SizeOf(zglTMikuSprite), random(10), @MikuInit, @MikuDraw, @MikuProc, @MikuFree);
+end;
+
+// RU: Óäàëèòü 100 ñïðàéòîâ.
+// EN: Delete 100 sprites.
+procedure DelMiku;
+  var
+    i: Integer;
+begin
+  // RU: Óäàëèì 100 ñïðàéòîâ ñî ñëó÷àéíûì ID.
+  // EN: Delete 100 sprites with random ID.
+  for i := 1 to 100 do
+    sengine2d_DelSprite(random(sengine2d.Count));
+end;
+
+procedure Init;
+  var
+    i: Integer;
+begin
+  texLogo := tex_LoadFromFile(dirRes + 'zengl.png');
+
+  texMiku := tex_LoadFromFile(dirRes + 'miku.png');
+  tex_SetFrameSize(texMiku, 128, 128);
+
+  // RU: Óñòàíàâëèâàåì òåêóùèì ìåíåäæåðîì ñïðàéòîâ ñâîé.
+  // EN: Set own sprite engine as current.
+  sengine2d_Set(@sengine2d);
+
+  // RU: Ñîçäàäèì 1000 ñïðàéòîâ Miku-chan :)
+  // EN: Create 1000 sprites of Miku-chan :)
+//  for i := 0 to 9 do
+//    AddMiku();
+
+  fntMain := font_LoadFromFile(dirRes + 'font.zfi');
+  setTextScale(15, fntMain);
+end;
+
+procedure Draw;
+begin
+//  batch2d_Begin();
+  // RU: Ðèñóåì âñå ñïðàéòû íàõîäÿùèåñÿ â òåêóùåì ñïðàéòîâîì ìåíåäæåðå.
+  // EN: Render all sprites contained in current sprite engine.
+  if time > 255 Then
+    sengine2d_Draw();
+
+  if time <= 255 Then
+    ssprite2d_Draw(texLogo, 400 - 256, 300 - 128, 512, 256, 0, time)
+  else
+    if time < 510 Then
+      begin
+        pr2d_Rect(0, 0, 800, 600, $000000, 510 - time, PR2D_FILL);
+        ssprite2d_Draw(texLogo, 400 - 256, 300 - 128, 512, 256, 0, 510 - time);
+      end;
+
+  if time > 255 Then
+    begin
+      pr2d_Rect(0, 0, 256, 64, $000000, 200, PR2D_FILL);
+      text_Draw(fntMain, 0, 0, 'FPS: ' + u_IntToStr(zgl_Get(RENDER_FPS)));
+      text_Draw(fntMain, 0, 20, 'Sprites: ' + u_IntToStr(sengine2d.Count));
+      text_Draw(fntMain, 0, 40, 'Up/Down - Add/Delete Miku :)');
+    end;
+//  batch2d_End();
+end;
+
+procedure Timer;
+begin
+  INC(time, 2);
+
+  // RU: Âûïîëíÿåì îáðàáîòêó âñåõ ñïðàéòîâ â òåêóùåì ñïðàéòîâîì ìåíåäæåðå.
+  // EN: Process all sprites contained in current sprite engine.
+  sengine2d_Proc();
+
+  // RU: Ïî íàæàòèþ ïðîáåëà î÷èñòèòü âñå ñïðàéòû.
+  // EN: Delete all sprites if space was pressed.
+  if key_Press(K_SPACE) Then sengine2d_ClearAll();
+  if key_Press(K_UP) Then AddMiku();
+  if key_Press(K_DOWN) Then DelMiku();
+
+  key_ClearState();
+end;
+
+procedure Quit;
+begin
+  // RU: Î÷èùàåì ïàìÿòü îò ñîçäàííûõ ñïðàéòîâ.
+  // EN: Free allocated memory for sprites.
+  sengine2d_Set(@sengine2d);
+  sengine2d_ClearAll();
+end;
+
+Begin
+  randomize;
+
+  TimeStart := timer_Add(@Timer, 16, Start);
+  TimeMiku := timer_Add(@AddMiku, 1000, SleepToStart, 10);
+
+  zgl_Reg(SYS_LOAD, @Init);
+  zgl_Reg(SYS_DRAW, @Draw);
+  zgl_Reg(SYS_EXIT, @Quit);
+
+  wnd_SetCaption(utf8_Copy('08 - Sprite Engine'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/08 - Sprite Engine/demo08_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo08</string>
+  <key>CFBundleIconFile</key>
+  <string>demo08</string>
+  <key>CFBundleName</key>
+  <string>demo08</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo08</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 7 - 0
Zengl_SRC/demos/FreePascal/08 - Sprite Engine/macosx_postbuild.sh

@@ -0,0 +1,7 @@
+# copy resources
+cp ../../../bin/data/zengl.png ../../../bin/demo08.app/Contents/Resources/
+cp ../../../bin/data/miku.png ../../../bin/demo08.app/Contents/Resources/
+cp ../../../bin/data/font* ../../../bin/demo08.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo08_macosx.plist ../../../bin/demo08.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo08.app/Contents/Resources/demo08.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/09 - Sprite Engine(Classes)/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo09.pas
+TARGET  = demo09
+TARGETW = demo09.exe
+TARGETM = demo09
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 206 - 0
Zengl_SRC/demos/FreePascal/09 - Sprite Engine(Classes)/demo09.pas

@@ -0,0 +1,206 @@
+program demo09;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  zglSpriteEngine,
+  zgl_screen,
+  zgl_window,
+  zgl_application,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_render_2d,
+  zgl_fx,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_sprite_2d,
+  zgl_primitives_2d,
+  zgl_font,
+  zgl_text,
+  zgl_types,
+  zgl_utils
+  ;
+
+type
+  CMiku = class(zglCSprite2D)
+  protected
+    FSpeed: zglTPoint2D;
+  public
+    procedure OnInit(_Texture: zglPTexture; _Layer: Integer); override;
+    procedure OnDraw; override;
+    procedure OnProc; override;
+    procedure OnFree; override;
+  end;
+
+var
+  dirRes   : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+  fntMain  : Byte;
+  texLogo  : zglPTexture;
+  texMiku  : zglPTexture;
+  time     : Integer;
+  sengine2d: zglCSEngine2D;
+  TimeStart : Byte;
+  TimeMiku  : Byte;
+
+// Miku
+procedure CMiku.OnInit(_Texture: zglPTexture; _Layer: Integer);
+begin
+  // RU: Óêàæåì ñâîþ òåêñòóðó è ñëîé äëÿ ñïðàéòà, çàîäíî óñòàíîâÿòñÿ ñòàíäàðòíûå ïàðàìåòðû âðîäå øèðèíû è âûñîòû íà îñíîâå äàííûõ î êàäðå â òåêñòóðå.
+  // EN: Set own texture and layer for sprite, also standard parameters will be set automatically(like width and height from info about texture).
+  inherited OnInit(texMiku, random(10));
+
+  X := 800 + random(800);
+  Y := random(600 - 128);
+  // RU: Çàäàåì ñêîðîñòü äâèæåíèÿ.
+  // EN: Set the moving speed.
+  FSpeed.X := -random(10) / 5 - 0.5;
+  FSpeed.Y := (random(10) - 5) / 5;
+end;
+
+procedure CMiku.OnDraw;
+begin
+  // RU: Ò.ê. ïî ñóòè ýòà ïðîöåäóðà îáúÿâëåíà òîëüêî äëÿ ïðèìåðà, òî âûçîâåì îñíîâíîé ìåòîä OnDraw êëàññà zglCSprite2D.
+  // EN: Because in fact, this procedure is declared only for example, so call to the main method OnDraw of class zglCSprite2D.
+  inherited;
+end;
+
+procedure CMiku.OnProc;
+begin
+  inherited;
+  X := X + FSpeed.X;
+  Y := Y + FSpeed.Y;
+  Frame := Frame + (abs(FSpeed.X) + abs(FSpeed.Y)) / 25;
+  if Frame > 8 Then
+    Frame := 1;
+
+  // RU: Åñëè ñïðàéò âûõîäèò çà ïðåäåëû ïî X, ñðàçó æå óäàëÿåì åãî.
+  // EN: Delete the sprite if it goes beyond X.
+  if X < -128 Then sengine2d.DelSprite(ID);
+
+  // RU: Åñëè ñïðàéò âûõîäèò çà ïðåäåëû ïî Y, ñòàâèì åãî â î÷åðåäü íà óäàëåíèå
+  // EN: Add sprite to queue for delete if it goes beyond Y.
+  if Y < -128 Then Kill := TRUE;
+  if Y > 600  Then Kill := TRUE;
+end;
+
+procedure CMiku.OnFree;
+begin
+  inherited;
+end;
+
+// RU: Äîáàâèòü 100 ñïðàéòîâ.
+// EN: Add 100 sprites.
+procedure AddMiku;
+  var
+    i, ID: Integer;
+begin
+  for i := 1 to 100 do
+    begin
+      // RU: Çàïðàøèâàåì ó ñïðàéòîâîãî ìåíåäæåðà íîâîå "ìåñòî" ïîä ñïðàéò :)
+      // EN: Request a "place" for a new sprite :)
+      ID := sengine2d.AddSprite();
+      // RU: Ñîçäàåì ýêçåìïëÿð ñïðàéòà CMiku. Àðãóìåíòàìè êîíñòðóêòîðà ÿâëÿþòñÿ ñàì ìåíåäæåð è áóäóùèé ID äëÿ ñïðàéòà.
+      // EN: Create a new CMiku. Constructor arguments must be current sprite engine and future ID for sprite.
+      sengine2d.List[ID] := CMiku.Create(sengine2d, ID);
+    end;
+end;
+
+// RU: Óäàëèòü 100 ñïðàéòîâ.
+// EN: Delete 100 sprites.
+procedure DelMiku;
+  var
+    i: Integer;
+begin
+  // RU: Óäàëèì 100 ñïðàéòîâ ñî ñëó÷àéíûì ID.
+  // EN: Delete 100 sprites with random ID.
+  for i := 1 to 100 do
+    sengine2d.DelSprite(random(sengine2d.Count));
+end;
+
+procedure Init;
+  var
+    i: Integer;
+begin
+  texLogo := tex_LoadFromFile(dirRes + 'zengl.png');
+
+  texMiku := tex_LoadFromFile(dirRes + 'miku.png');
+  tex_SetFrameSize(texMiku, 128, 128);
+
+  // RU: Ñîçäàåì ýêçåìïëÿð zglCSEngine2D.
+  // EN: Create zglCSEngine2D object.
+  sengine2d := zglCSEngine2D.Create();
+
+  // RU: Ñîçäàäèì 1000 ñïðàéòîâ Miku-chan :)
+  // EN: Create 1000 sprites of Miku-chan :)
+//  for i := 0 to 9 do
+//    AddMiku();
+
+  fntMain := font_LoadFromFile(dirRes + 'font.zfi');
+end;
+
+procedure Draw;
+begin
+  setTextScale(15, fntMain);
+//  batch2d_Begin();
+  // RU: Ðèñóåì âñå ñïðàéòû íàõîäÿùèåñÿ â òåêóùåì ñïðàéòîâîì ìåíåäæåðå.
+  // EN: Render all sprites contained in current sprite engine.
+  if time > 255 Then
+    sengine2d.Draw();
+
+  if time <= 255 Then
+    ssprite2d_Draw(texLogo, 400 - 256, 300 - 128, 512, 256, 0, time)
+  else
+    if time < 510 Then
+      begin
+        pr2d_Rect(0, 0, 800, 600, $000000, 510 - time, PR2D_FILL);
+        ssprite2d_Draw(texLogo, 400 - 256, 300 - 128, 512, 256, 0, 510 - time);
+      end;
+
+  if time > 255 Then
+    begin
+      pr2d_Rect(0, 0, 256, 64, $000000, 200, PR2D_FILL);
+      text_Draw(fntMain, 0, 0, 'FPS: ' + u_IntToStr(zgl_Get(RENDER_FPS)));
+      text_Draw(fntMain, 0, 20, 'Sprites: ' + u_IntToStr(sengine2d.Count));
+      text_Draw(fntMain, 0, 40, 'Up/Down - Add/Delete Miku :)');
+    end;
+//  batch2d_End();
+end;
+
+procedure Timer;
+begin
+  INC(time, 2);
+
+  // RU: Âûïîëíÿåì îáðàáîòêó âñåõ ñïðàéòîâ â òåêóùåì ñïðàéòîâîì ìåíåäæåðå.
+  // EN: Process all sprites contained in current sprite engine.
+  sengine2d.Proc();
+
+  // RU: Ïî íàæàòèþ ïðîáåëà î÷èñòèòü âñå ñïðàéòû.
+  // EN: Delete all sprites if space was pressed.
+  if key_Press(K_SPACE) Then sengine2d.ClearAll();
+  if key_Press(K_UP) Then AddMiku();
+  if key_Press(K_DOWN) Then DelMiku();
+
+  key_ClearState();
+end;
+
+procedure Quit;
+begin
+  // RU: Î÷èùàåì ïàìÿòü îò ñîçäàííûõ ñïðàéòîâ.
+  // EN: Free allocated memory for sprites.
+  sengine2d.Destroy();
+end;
+
+Begin
+  randomize();
+
+  TimeStart := timer_Add( @Timer, 16, Start );
+  TimeMiku := timer_Add( @AddMiku, 1000, SleepToStart, 10 );
+
+  zgl_Reg(SYS_LOAD, @Init);
+  zgl_Reg(SYS_DRAW, @Draw);
+  zgl_Reg(SYS_EXIT, @Quit);
+
+  wnd_SetCaption(utf8_Copy('09 - Sprite Engine(Classes)'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/09 - Sprite Engine(Classes)/demo09_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo09</string>
+  <key>CFBundleIconFile</key>
+  <string>demo09</string>
+  <key>CFBundleName</key>
+  <string>demo09</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo09</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 7 - 0
Zengl_SRC/demos/FreePascal/09 - Sprite Engine(Classes)/macosx_postbuild.sh

@@ -0,0 +1,7 @@
+# copy resources
+cp ../../../bin/data/zengl.png ../../../bin/demo09.app/Contents/Resources/
+cp ../../../bin/data/miku.png ../../../bin/demo09.app/Contents/Resources/
+cp ../../../bin/data/font* ../../../bin/demo09.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo09_macosx.plist ../../../bin/demo09.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo09.app/Contents/Resources/demo09.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/10 - Tiles/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo10.pas
+TARGET  = demo10
+TARGETW = demo10.exe
+TARGETM = demo10
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 90 - 0
Zengl_SRC/demos/FreePascal/10 - Tiles/demo10.pas

@@ -0,0 +1,90 @@
+program demo10;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_fx,
+  zgl_file,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_textures_jpg,
+  zgl_tiles_2d,
+  zgl_font,
+  zgl_text,
+  zgl_math_2d,
+  zgl_utils
+  ;
+
+var
+  dirRes  : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+  fntMain : Byte;
+  map     : zglTTiles2D;
+  texTiles: zglPTexture;
+  TimeStart: Byte;
+
+procedure Init;
+  var
+    i, j: Integer;
+    f   : zglTFile;
+begin
+  fntMain := font_LoadFromFile(dirRes + 'font.zfi');
+
+  texTiles := tex_LoadFromFile(dirRes + 'tiles.png');
+  tex_SetFrameSize(texTiles, 32, 32);
+
+  // RU: Èíèöèàëèçàöèÿ òàéëîâ ðàçìåðîì 32x32. Ïàðàìåòð Count óêàçûâàåò íà êîëè÷åñòâî òàéëîâ ïî X è Y. Ìàññèâ Tiles ñîäåðæèò êàäðû äëÿ êàæäîãî òàéëà.
+  // EN: Initialization of tiles with size 32x32. Parameter Count set amount of tiles on X and Y. Array Tiles contains frames for every tile.
+  map.Width  := 32;
+  map.Height  := 32;
+  map.X := 25;
+  map.Y := 19;
+  SetLength(map.Tiles, map.X, map.Y);
+  // RU: Çàïîëíÿåì êàðòó "òðàâîé", 19 êàäð.
+  // EN: Fill the map by "grass", 19 frame.
+  for i := 0 to map.X - 1 do
+    for j := 0 to map.Y - 1 do
+      map.Tiles[i, j] := 19;
+
+  // RU: Çàãðóæàåì êàðòó èç áèíàðíîãî ôàéëà.
+  // EN: Load map from binary file.
+  file_Open(f, dirRes + 'ground.map', FOM_OPENR);
+  for i := 0 to map.X - 1 do
+    file_Read(f, map.Tiles[i, 0], map.Y * SizeOf(Integer));
+  file_Close(f);
+  setTextScale(15, fntMain);
+end;
+
+procedure Draw;
+begin
+  // RU: Ðåíäåðèì òàéëû â êîîðäèíàòàõ 0,0.
+  // EN: Render tiles in coordinates 0,0.
+  tiles2d_Draw(texTiles, 0, 0, @map);
+
+  text_Draw(fntMain, 0, 0, 'FPS: ' + u_IntToStr(zgl_Get(RENDER_FPS)));
+
+  text_Draw(fntMain, 180, 30, 'This is a tarrible example of tile map, but main idea should be clear :)');
+end;
+
+procedure Timer;
+begin
+//  if key_Press(K_ESCAPE) Then winOn := FALSE;
+
+  key_ClearState();
+end;
+
+Begin
+  randomize();
+
+  TimeStart := timer_Add(@Timer, 16, Start);
+
+  zgl_Reg(SYS_LOAD, @Init);
+  zgl_Reg(SYS_DRAW, @Draw);
+
+  wnd_SetCaption(utf8_Copy('10 - Tiles'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/10 - Tiles/demo10_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo11</string>
+  <key>CFBundleIconFile</key>
+  <string>demo10</string>
+  <key>CFBundleName</key>
+  <string>demo10</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo10</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 7 - 0
Zengl_SRC/demos/FreePascal/10 - Tiles/macosx_postbuild.sh

@@ -0,0 +1,7 @@
+# copy resources
+cp ../../../bin/data/ground.map ../../../bin/demo10.app/Contents/Resources/
+cp ../../../bin/data/tiles.png ../../../bin/demo10.app/Contents/Resources/
+cp ../../../bin/data/font* ../../../bin/demo10.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo10_macosx.plist ../../../bin/demo10.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo10.app/Contents/Resources/demo10.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/11 - Grid/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo11.pas
+TARGET  = demo11
+TARGETW = demo11.exe
+TARGETM = demo11
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 100 - 0
Zengl_SRC/demos/FreePascal/11 - Grid/demo11.pas

@@ -0,0 +1,100 @@
+program demo11;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_fx,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_textures_jpg,
+  zgl_grid_2d,
+  zgl_font,
+  zgl_text,
+  zgl_math_2d,
+  zgl_utils
+  ;
+
+var
+  dirRes     : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+  fntMain    : Byte;
+  texBack    : zglPTexture;
+  grid       : zglTGrid2D;
+  wave       : Single;
+  TimeStart  : Byte;
+
+procedure Init;
+  var
+    i, j: Integer;
+begin
+  texBack := tex_LoadFromFile(dirRes + 'back04.jpg');
+
+  fntMain := font_LoadFromFile(dirRes + 'font.zfi');
+
+  // RU: Èíèöèàëèçàöèÿ ñåòêè ðàçìåðîì 21x16. Îñíîâíàÿ èäåÿ - êàæäûé óçåë ñåòêè ýòî ñìåùåíèå îòíîñèòåëüíî å¸ âåðõíåãî ëåâîãî óãëà.
+  // EN: Initialization of grid with size 21x16. Main idea - every node of grid is an offset from the top left corner.
+  grid.Cols := 21;
+  grid.Rows := 16;
+  SetLength(grid.Grid, grid.Cols, grid.Rows);
+  for i := 0 to grid.Cols - 1 do
+    for j := 0 to grid.Rows - 1 do
+      begin
+        grid.Grid[i, j].X := i * 40;
+        grid.Grid[i, j].Y := j * 40;
+      end;
+
+  setTextScale(15, fntMain);
+end;
+
+procedure Draw;
+begin
+  // RU: Ðåíäåðèì ñåòêó â êîîðäèíàòàõ 0,0.
+  // EN: Render grid in coordinates 0,0.
+  sgrid2d_Draw(texBack, 0, 0, @grid);
+
+  text_Draw(fntMain, 0, 0, 'FPS: ' + u_IntToStr(zgl_Get(RENDER_FPS)));
+end;
+
+procedure Timer;
+  var
+    i, j: Integer;
+    cwave, swave: Single;
+begin
+  wave  := wave + random(1000) / 10000;
+  cwave := cos(wave);
+  swave := sin(wave);
+
+  // RU: Ñèìóëÿöèÿ ïðîñòîãî ýôôåêòà ïîä âîäîé.
+  // EN: Simulation of simple underwater effect.
+  for i := 1 to grid.Cols - 2 do
+    for j := 1 to grid.Rows - 2 do
+    begin
+      if (i mod 2 = 0) and (j mod 2 = 0) Then
+      begin
+        grid.Grid[i, j].X := i * 40 + cwave;
+        grid.Grid[i, j].Y := j * 40 + swave;
+      end else
+      begin
+        grid.Grid[i, j].X := i * 40 - cwave;
+        grid.Grid[i, j].Y := j * 40 - swave;
+      end;
+    end;
+
+  key_ClearState();
+end;
+
+Begin
+  randomize();
+
+  TimeStart := timer_Add(@Timer, 16, SleepToStart, 3);
+
+  zgl_Reg(SYS_LOAD, @Init);
+  zgl_Reg(SYS_DRAW, @Draw);
+
+  wnd_SetCaption(utf8_Copy('11 - Grid'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/11 - Grid/demo11_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo11</string>
+  <key>CFBundleIconFile</key>
+  <string>demo11</string>
+  <key>CFBundleName</key>
+  <string>demo11</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo11</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 9 - 0
Zengl_SRC/demos/FreePascal/11 - Grid/macosx_postbuild.sh

@@ -0,0 +1,9 @@
+# copy resources
+cp ../../../bin/data/back04.jpg ../../../bin/demo11.app/Contents/Resources/
+cp ../../../bin/data/font* ../../../bin/demo11.app/Contents/Resources/
+# copy binary into bundle
+rm ../../../bin/demo11.app/Contents/MacOS/demo11
+cp ../../../bin/demo11 ../../../bin/demo11.app/Contents/MacOS/demo11
+# make Info.plist and copy icon
+cp -f demo11_macosx.plist ../../../bin/demo11.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo11.app/Contents/Resources/demo11.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/12 - Render into Texture/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo12.pas
+TARGET  = demo12
+TARGETW = demo12.exe
+TARGETM = demo12
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 90 - 0
Zengl_SRC/demos/FreePascal/12 - Render into Texture/demo12.pas

@@ -0,0 +1,90 @@
+program demo12;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_render_2d,
+  zgl_fx,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_render_target,
+  zgl_sprite_2d,
+  zgl_font,
+  zgl_text,
+  zgl_math_2d,
+  zgl_utils
+  ;
+
+var
+  dirRes   : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+  fntMain  : Byte;
+  texTux   : zglPTexture;
+  rtFull   : zglPRenderTarget;
+  rtDefault: zglPRenderTarget;
+  TimeStart: Byte;
+
+procedure Init;
+begin
+  texTux := tex_LoadFromFile(dirRes + 'tux_stand.png');
+  tex_SetFrameSize(texTux, 64, 64);
+
+  fntMain := font_LoadFromFile(dirRes + 'font.zfi');
+
+  // RU: Ñîçäàåì RenderTarget è "öåïëÿåì" ïóñòóþ òåêñòóðó. Â ïðîöåññå òåêñòóðó ìîæíî ñìåíèòü ïðèñâîèâ rtarget.Surface äðóãóþ zglPTexture, ãëàâíîå ÷òî áû ñîâïàäàëè ðàçìåðû ñ òåìè, ÷òî óêàçàíû â
+  //     tex_CreateZero. Òàðãåòó òàêæå óêàçàí ôëàã RT_FULL_SCREEN, îòâå÷àþùèé çà òî, ÷òî áû â òåêñòóðó ïîìåùàëîñü âñå ñîäåðæèìîå ýêðàíà à íå îáëàñòü 256x256(êàê ñ ôëàãîì RT_DEFAULT).
+  // EN: Create a RenderTarget and "bind" empty texture to it. Later texture can be changed via changing rtarget.Surface to another zglPTexture, the only requirement - the same size, that was
+  //     set in tex_CreateZero. Also target use flag RT_FULL_SCREEN that responsible for rendering whole content of screen into target, not only region 256x256(like with flag RT_DEFAULT).
+  rtFull := rtarget_Add(tex_CreateZero(256, 256), RT_FULL_SCREEN);
+
+  // RU: Äëÿ ñðàâíåíèÿ ñîçäàäèì åù¸ îäèí RenderTarget ñ ôëàãîì RT_DEFAULT.
+  // EN: Create one more RenderTarget with flag RT_DEFAULT for comparison.
+  rtDefault := rtarget_Add(tex_CreateZero(256, 256), RT_DEFAULT);
+
+  setTextScale(15, fntMain);
+end;
+
+procedure Draw;
+begin
+  // RU: Óñòàíàâëèâàåì òåêóùèé RenderTarget.
+  // EN: Set current RenderTarget.
+  rtarget_Set(rtFull);
+  // RU: Ðèñóåì â íåãî.
+  // EN: Render to it.
+  asprite2d_Draw(texTux, random(800 - 64), random(600 - 64), 64, 64, 0, random(9) + 1);
+  // RU: Âîçâðàùàåìñÿ ê îáû÷íîìó ðåíäåðó.
+  // EN: Return to default rendering.
+  rtarget_Set(nil);
+
+  rtarget_Set(rtDefault);
+  asprite2d_Draw(texTux, random(800 - 64), random(600 - 64), 64, 64, 0, random(9) + 1);
+  rtarget_Set(nil);
+
+  // RU: Òåïåðü ðèñóåì ñîäåðæèìîå RenderTarget'îâ.
+  // EN: Render content of RenderTargets.
+  ssprite2d_Draw(rtFull.Surface, (400 - 256) / 2, (600 - 256) / 2, 256, 256, 0);
+  ssprite2d_Draw(rtDefault.Surface, (400 - 256) / 2 + 400, (600 - 256) / 2, 256, 256, 0);
+
+  text_Draw(fntMain, 0, 0, 'FPS: ' + u_IntToStr(zgl_Get(RENDER_FPS)));
+end;
+
+procedure Timer;
+begin
+  key_ClearState();
+end;
+
+Begin
+  randomize();
+
+  TimeStart := timer_Add(@Timer, 16, Start);
+
+  zgl_Reg(SYS_LOAD, @Init);
+  zgl_Reg(SYS_DRAW, @Draw);
+
+  wnd_SetCaption(utf8_Copy('12 - Render into Texture'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/12 - Render into Texture/demo12_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo12</string>
+  <key>CFBundleIconFile</key>
+  <string>demo12</string>
+  <key>CFBundleName</key>
+  <string>demo12</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo12</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 6 - 0
Zengl_SRC/demos/FreePascal/12 - Render into Texture/macosx_postbuild.sh

@@ -0,0 +1,6 @@
+# copy resources
+cp ../../../bin/data/tux_stand.png ../../../bin/demo12.app/Contents/Resources/
+cp ../../../bin/data/font* ../../../bin/demo12.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo12_macosx.plist ../../../bin/demo12.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo12.app/Contents/Resources/demo12.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/13 - Particles/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo13.pas
+TARGET  = demo13
+TARGETW = demo13.exe
+TARGETM = demo13
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 131 - 0
Zengl_SRC/demos/FreePascal/13 - Particles/demo13.pas

@@ -0,0 +1,131 @@
+program demo13;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_render_2d,
+  zgl_fx,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_textures_jpg,
+  zgl_sprite_2d,
+  zgl_particles_2d,
+  zgl_primitives_2d,
+  zgl_font,
+  zgl_text,
+  zgl_math_2d,
+  zgl_utils
+  ;
+
+var
+  dirRes        : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+  fntMain       : Byte;
+  texBack       : zglPTexture;
+  debug         : Boolean;
+  particles     : zglTPEngine2D;
+  emitterFire   : array[0..2] of zglPEmitter2D;
+  emitterDiamond: zglPEmitter2D;
+  emitterRain   : zglPEmitter2D;
+  TimeStart     : Byte;
+
+procedure Init;
+begin
+  texBack := tex_LoadFromFile(dirRes + 'back02.png');
+
+  fntMain := font_LoadFromFile(dirRes + 'font.zfi');
+
+  // EN: Load three types of fire emitters.
+  // RU: Çàãðóçêà òð¸õ ðàçíûõ âèäîâ ýìèòòåðîâ îãíÿ.
+  emitterFire[0] := emitter2d_LoadFromFile(dirRes + 'emitter_fire00.zei');
+  emitterFire[1] := emitter2d_LoadFromFile(dirRes + 'emitter_fire01.zei');
+  emitterFire[2] := emitter2d_LoadFromFile(dirRes + 'emitter_fire02.zei');
+
+  // EN: Set own particels engine.
+  // RU: Óñòàíîâêà ñîáñòâåííîãî äâèæêà ýìèòòåðîâ.
+  pengine2d_Set(@particles);
+
+  // EN: Add 6 fire emitters to particles engine. Second parameter of function returns pointer to instance of new emitter, which can be processed manually.
+  //     This instance will be nil after the death, so check everything.
+  // RU: Äîáàâëÿåì â äâèæîê 6 ýìèòòåðîâ îãíÿ. Âòîðîé ïàðàìåòð ôóíêöèè ïîçâîëÿåò ïîëó÷èòü óêàçàòåëü íà êîíêðåòíûé ýêçåìïëÿð ýìèòòåðà, êîòîðûé ìîæíî áóäåò îáðàáàòûâàòü âðó÷íóþ.
+  //     Äàííûé ýêçåìïëÿð ïîñëå ñìåðòè áóäåò ñîäåðæàòü nil, ïîýòîìó èñïîëüçóéòå ïðîâåðêó.
+  pengine2d_AddEmitter(emitterFire[0], nil, 642, 190);
+  pengine2d_AddEmitter(emitterFire[0], nil, 40, 368);
+  pengine2d_AddEmitter(emitterFire[0], nil, 246, 368);
+  pengine2d_AddEmitter(emitterFire[1], nil, 532, 244);
+  pengine2d_AddEmitter(emitterFire[1], nil, 318, 422);
+  pengine2d_AddEmitter(emitterFire[1], nil, 583, 420);
+  pengine2d_AddEmitter(emitterFire[2], nil, 740, 525);
+
+  emitterDiamond := emitter2d_LoadFromFile(dirRes + 'emitter_diamond.zei');
+  pengine2d_AddEmitter(emitterDiamond, nil);
+
+  emitterRain := emitter2d_LoadFromFile(dirRes + 'emitter_rain.zei');
+  pengine2d_AddEmitter(emitterRain, nil);
+
+  setTextScale(15, fntMain);
+end;
+
+procedure Draw;
+  var
+    i: Integer;
+begin
+  batch2d_Begin();
+
+  ssprite2d_Draw(texBack, 0, 0, 800, 600, 0);
+
+  // EN: Rendering of all emitters in current particles engine.
+  // RU: Ðåíäåðèíã âñåõ ýìèòòåðîâ â òåêóùåì äâèæêå ÷àñòèö.
+  pengine2d_Draw();
+
+  if debug Then
+    for i := 0 to particles.Count.Emitters - 1 do
+      with particles.List[i].BBox do
+        pr2d_Rect(MinX, MinY, MaxX - MinX, MaxY - MinY, $FF0000, 255);
+
+  text_Draw(fntMain, 0, 0, 'FPS: ' + u_IntToStr(zgl_Get(RENDER_FPS)));
+  text_Draw(fntMain, 0, 20, 'Particles: ' + u_IntToStr(particles.Count.Particles));
+  text_Draw(fntMain, 0, 40, 'Debug(F1): ' + u_BoolToStr(debug));
+
+  batch2d_End();
+end;
+
+procedure Timer;
+begin
+  if key_Press(K_F1) Then debug := not debug;
+
+  key_ClearState();
+end;
+
+procedure Update(dt: Double);
+begin
+  // EN: Process all emitters in current particles engine.
+  // RU: Îáðàáîòêà âñåõ ýìèòòåðîâ â òåêóùåì äâèæêå ÷àñòèö.
+  pengine2d_Proc(dt);
+end;
+
+procedure Quit;
+begin
+  // RU: Î÷èùàåì ïàìÿòü îò ñîçäàííûõ ýìèòòåðîâ.
+  // EN: Free allocated memory for emitters.
+  pengine2d_Set(@particles);
+  pengine2d_ClearAll();
+end;
+
+Begin
+  randomize();
+
+  TimeStart := timer_Add(@Timer, 16, Start);
+
+  zgl_Reg(SYS_LOAD, @Init);
+  zgl_Reg(SYS_DRAW, @Draw);
+  zgl_Reg(SYS_UPDATE, @Update);
+  zgl_Reg(SYS_EXIT, @Quit);
+
+  wnd_SetCaption(utf8_Copy('13 - Particles'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/13 - Particles/demo13_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo13</string>
+  <key>CFBundleIconFile</key>
+  <string>demo13</string>
+  <key>CFBundleName</key>
+  <string>demo13</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo13</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 8 - 0
Zengl_SRC/demos/FreePascal/13 - Particles/macosx_postbuild.sh

@@ -0,0 +1,8 @@
+# copy resources
+cp ../../../bin/data/back02.png ../../../bin/demo13.app/Contents/Resources/
+cp ../../../bin/data/font* ../../../bin/demo13.app/Contents/Resources/
+cp ../../../bin/data/emitter_* ../../../bin/demo13.app/Contents/Resources/
+cp ../../../bin/data/particle.png ../../../bin/demo13.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo13_macosx.plist ../../../bin/demo13.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo13.app/Contents/Resources/demo13.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/14 - Sound/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo14.pas
+TARGET  = demo14
+TARGETW = demo14.exe
+TARGETM = demo14
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 167 - 0
Zengl_SRC/demos/FreePascal/14 - Sound/demo14.pas

@@ -0,0 +1,167 @@
+program demo14;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_mouse,
+  zgl_render_2d,
+  zgl_fx,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_font,
+  zgl_text,
+  zgl_sprite_2d,
+  zgl_sound,
+  zgl_sound_wav,
+  zgl_sound_ogg,
+  zgl_types,
+  zgl_collision_2d,
+  zgl_utils,
+  zgl_memory
+  ;
+
+const
+  SCREEN_WIDTH  = 800;
+  SCREEN_HEIGHT = 600;
+
+var
+  dirRes : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+  fntMain: Byte;
+  icon   : array[0..1] of zglPTexture;
+  sound  : zglPSound;
+  audio  : Integer;
+  state  : Integer;
+
+  musicMem: zglTMemory;
+
+  // äîáàâëÿåì íîìåð çâóêà, ïîêà äëÿ îäíîãî çâóêà
+  IDSound: Integer;
+  TimeStart: Byte;
+
+// RU: Ò.ê. çâóêîâàÿ ïîäñèñòåìà íàöåëåíà íà 3D, äëÿ ïîçèöèîíèðîâàíèÿ çâóêîâ â 2D íóæíû íåêîòîðûå óõèùðåíèÿ.
+// EN: Because sound subsystem using 3D, there is some tricky way to calculate sound position in 2D.
+function CalcX2D(const X: Single): Single;
+begin
+  Result := (X - SCREEN_WIDTH / 2) * (20 / SCREEN_WIDTH / 2);          // ñìåíèë ñìåùåíèå ïî X è Y, òåïåðü áîëåå ÿâíî ìîæíî
+end;                                                                    // îòäàëèòü/ïðèáëèçèòü çâóê
+
+function CalcY2D(const Y: Single): Single;
+begin
+  Result := (Y - SCREEN_HEIGHT / 2) * (20 / SCREEN_HEIGHT / 2);
+end;
+
+procedure Init;
+begin
+  // RU: Èíèöèàëèçèðóåì çâóêîâóþ ïîäñèñòåìó. Äëÿ Windows ìîæíî ñäåëàòü âûáîð ìåæäó DirectSound è OpenAL îòðåäàêòèðîâàâ ôàéë zgl_config.cfg.
+  // EN: Initializing sound subsystem. For Windows can be used DirectSound or OpenAL, see zgl_config.cfg.
+  snd_Init();
+
+  // RU: Çàãðóæàåì çâóêîâîé ôàéë è óñòàíàâëèâàåì äëÿ íåãî ìàêñèìàëüíîe êîëè÷åñòâî ïðîèãðûâàåìûõ èñòî÷íèêîâ â 2.
+  // EN: Load the sound file and set maximum count of sources that can be played to 2.
+  sound := snd_LoadFromFile(dirRes + 'click.wav', 2);
+
+  // RU: Çàãðóæàåì òåêñòóðû, êîòîðûå áóäóò èíäèêàòîðàìè.
+  // EN: Load the textures, that will be indicators.
+  icon[0] := tex_LoadFromFile(dirRes + 'audio-stop.png');
+  icon[1] := tex_LoadFromFile(dirRes + 'audio-play.png');
+
+  fntMain := font_LoadFromFile(dirRes + 'font.zfi');
+  setTextScale(15, fntMain);
+end;
+
+procedure Draw;
+  var
+    r: zglTRect;
+begin
+  ssprite2d_Draw(icon[state], (SCREEN_WIDTH - 128) / 2, (SCREEN_HEIGHT - 128) / 2, 128, 128, 0);
+  text_Draw(fntMain, SCREEN_WIDTH / 2, SCREEN_HEIGHT / 2 + 64, 'Skillet - Comatose - Whispers In The Dark', TEXT_HALIGN_CENTER);
+
+  r.X := (SCREEN_WIDTH - 128) / 2;
+  r.Y := (SCREEN_HEIGHT - 128) / 2;
+  r.W := 128;
+  r.H := 128;
+  if col2d_PointInRect(mouseX, mouseY, r) Then
+    begin
+      fx_SetBlendMode(FX_BLEND_ADD);
+      ssprite2d_Draw(icon[state], (SCREEN_WIDTH - 132) / 2, (SCREEN_HEIGHT - 132) / 2, 132, 132, 0, 155);
+      fx_SetBlendMode(FX_BLEND_NORMAL);
+    end;
+end;
+
+procedure Timer;
+  var
+    r: zglTRect;
+    p: Integer;
+begin
+  // RU: Ïðîâåðÿåì èãðàåò ëè ìóçûêà(1 - èãðàåò, 0 - íå èãðàåò). Òàê æå ìîæíî ïðîâåðèòü è çâóêè - ïîäñòàâèâ zglPSound è ID âîò òàê:
+  //     snd_Get(Sound, ID...
+  //     ID âîçâðàùàåòñÿ ôóíêöèåé snd_Play
+  //
+  // EN: Check if music playing(1 - playing, 0 - not playing). Sounds also can be checked this way - just use zglPSound and ID:
+  //     snd_Get(Sound, ID...
+  //     ID returns by function snd_Play.
+  state := snd_Get(SND_STREAM, audio, SND_STATE_PLAYING);
+  if state = 0 Then
+    audio := 0;
+
+  if mBClickCanClick(M_BLEFT_CLICK) Then
+  begin
+      // RU:  äàííîì ñëó÷àå ìû íà÷èíàåì âîñïðîèçâîäèòü çâóê ñðàçó â óêàçàííûõ êîîðäèíàòàõ, íî èõ ìîæíî ìåíÿòü è â ïðîöåññå èñïîëüçóÿ ïðîöåäóðó snd_SetPos.
+      //     Âàæíî: Äëÿ OpenAL ìîæíî ïîçèöèîíèðîâàòü òîëüêî mono-çâóêè
+      //
+      // EN: In this case, we begin to play the sound directly in these coordinates, but they can be changed later using procedure snd_SetPos.
+      //     Important: OpenAL can position only mono-sounds.
+
+// ýòà ÷àñòü èçìåíåíà!!! Òåïåðü ìîæíî çàíîâî âîñïðîèçâîäèòü çâóêè, äàæå åñëè îíè íå çàêîí÷èëè èãðàòü.
+    if snd_Get(sound, IDSound, SND_STATE_PLAYING) = IDSound then
+      snd_Stop(sound, IDSound);
+    IDSound := snd_Play(sound, FALSE, CalcX2D(mouse_X), CalcY2D(mouse_Y));
+// ------------------------------------------------------------------------------------------
+
+    r.X := (SCREEN_WIDTH - 128) / 2;
+    r.Y := (SCREEN_HEIGHT - 128) / 2;
+    r.W := 128;
+    r.H := 128;
+
+// äîáàâëÿåì ïðîâåðêó íà ïðîèãðûâàíèå çâóêà, òîëüêî åñëè ìíîãî ðàçâíûõ çâóêîâ/ìóçûêè, òî íîìåðà íàäî ìåíÿòü (íå òîëüêî 1!!!)
+    if col2d_PointInRect(mouse_X, mouse_Y, r) and (audio = 1) Then
+    begin
+      p := snd_Get(SND_STREAM, audio, SND_STATE_PLAYING);
+      if p = 1 then
+        snd_StopStream(audio);
+    end;
+// ---------------------------------------------------------------------------------------------------------------
+
+    if col2d_PointInRect(mouse_X, mouse_Y, r) and (audio = 0) Then
+      audio := snd_PlayFile(dirRes + 'music.ogg');
+
+  end;
+
+  // RU: Ïîëó÷àåì â ïðîöåíòàõ ïîçèöèþ ïðîèãðûâàíèÿ àóäèîïîòîêà è ñòàâèì ãðîìêîñòü äëÿ ïëàâíûõ ïåðåõîäîâ.
+  // EN: Get position in percent's for audio stream and set volume for smooth playing.
+  p := snd_Get(SND_STREAM, audio, SND_STATE_PERCENT);
+  if (p >= 0) and (p < 25) Then
+    snd_SetVolume(SND_STREAM, audio, (1 / 24) * p);
+  if (p >= 75) and (p < 100) Then
+    snd_SetVolume(SND_STREAM, audio, 1 - (1 / 24) * (p - 75));
+
+  key_ClearState();
+  mouse_ClearState();
+end;
+
+Begin
+  randomize();
+
+  TimeStart := timer_Add(@Timer, 16, Start);
+
+  zgl_Reg(SYS_LOAD, @Init);
+  zgl_Reg(SYS_DRAW, @Draw);
+
+  wnd_SetCaption(utf8_Copy('14 - Sound'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/14 - Sound/demo14_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo14</string>
+  <key>CFBundleIconFile</key>
+  <string>demo14</string>
+  <key>CFBundleName</key>
+  <string>demo14</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo14</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 9 - 0
Zengl_SRC/demos/FreePascal/14 - Sound/macosx_postbuild.sh

@@ -0,0 +1,9 @@
+# copy resources
+cp ../../../bin/data/click.wav ../../../bin/demo14.app/Contents/Resources/
+cp ../../../bin/data/music.ogg ../../../bin/demo14.app/Contents/Resources/
+cp ../../../bin/data/audio-stop.png ../../../bin/demo14.app/Contents/Resources/
+cp ../../../bin/data/audio-play.png ../../../bin/demo14.app/Contents/Resources/
+cp ../../../bin/data/font* ../../../bin/demo14.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo14_macosx.plist ../../../bin/demo14.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo14.app/Contents/Resources/demo14.icns

+ 83 - 0
Zengl_SRC/demos/FreePascal/15 - Video/Makefile

@@ -0,0 +1,83 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo15.pas
+TARGET  = demo15
+TARGETW = demo15.exe
+TARGETM = demo15
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 94 - 0
Zengl_SRC/demos/FreePascal/15 - Video/demo15.pas

@@ -0,0 +1,94 @@
+program demo15;
+
+{$I zglCustomConfig.cfg}
+
+uses
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_mouse,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_font,
+  zgl_text,
+  zgl_primitives_2d,
+  zgl_sprite_2d,
+  zgl_video,
+  zgl_video_theora,
+  zgl_utils
+  ;
+
+var
+  dirRes   : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+  fntMain  : Byte;
+  video    : zglPVideoStream;
+  videoSeek: Boolean;
+  TimeStart: Byte;
+
+procedure Init;
+begin
+  fntMain := font_LoadFromFile(dirRes + 'font.zfi');
+
+  // EN: Open the video file.
+  // RU: Îòêðûòü âèäåî ôàéë.
+  video := video_OpenFile(dirRes + 'video.ogv');
+
+  setTextScale(15, fntMain);
+end;
+
+procedure Draw;
+begin
+  if Assigned(video) Then
+    begin
+      // EN: Rendering the current video frame in the center of screen using parameters of it from video.Info.
+      // RU: Ðåíäåðèíã òåêóùåãî êàäðà âèäåî â öåíòðå ýêðàíà èñïîëüçóÿ ïàðàìåòðû èç video.Info.
+      ssprite2d_Draw(video.Texture, (800 - video.Info.Width) / 2, (600 - video.Info.Height) / 2, video.Info.Width, video.Info.Height, 0);
+
+      // EN: Rendering of progress bar.
+      // RU: Ðåíäåðèíã ïîëîñû ïðîãðåññà.
+      pr2d_Rect(0, 600 - 100, 800, 20, $00FF00, 255);
+      pr2d_Rect(0, 600 - 100, (800 / video.Info.Duration) * video.Time, 20, $00FF00, 155, PR2D_FILL);
+
+      text_Draw(fntMain, 0, 0, 'FPS: ' + u_IntToStr(zgl_Get(RENDER_FPS)));
+      text_Draw(fntMain, 0, 20, 'Frame: ' + u_IntToStr(video.Frame));
+      text_Draw(fntMain, 100, 0, 'Duration: ' + u_FloatToStr(video.Info.Duration / 1000));
+      text_Draw(fntMain, 100, 20, 'Frames: ' + u_IntToStr(video.Info.Frames));
+      text_Draw(fntMain, 230, 0, 'Time: ' + u_FloatToStr(video.Time / 1000));
+    end;
+end;
+
+procedure Timer;
+begin
+    // EN: If left mouse button is down on progress bar, then seek the video.
+  // RU: Åñëè çàæàòà ëåâàÿ êíîïêà ìûøè íàä ïîëîñîé ïðîãðåññà - ïåðåìåùàòüñÿ ïî âèäåî.
+  if mBUpDown(M_BLEFT_DOWN) and (mouse_Y > 500) and (mouse_Y < 520) Then
+  begin
+    videoSeek := TRUE;
+    video_Seek(video, (mouse_X / 800) * video.Info.Duration);
+  end else
+    videoSeek := FALSE;
+
+  key_ClearState();
+  mouse_ClearState();
+end;
+
+procedure Update(dt: Double);
+begin
+  if not videoSeek Then
+    video_Update(video, dt, TRUE);
+end;
+
+Begin
+  randomize();
+
+  TimeStart := timer_Add(@Timer, 16, Start);
+
+  zgl_Reg(SYS_LOAD, @Init);
+  zgl_Reg(SYS_DRAW, @Draw);
+  zgl_Reg(SYS_UPDATE, @Update);
+
+  wnd_SetCaption(utf8_Copy('15 - Video'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/15 - Video/demo15_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo15</string>
+  <key>CFBundleIconFile</key>
+  <string>demo15</string>
+  <key>CFBundleName</key>
+  <string>demo15</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo15</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 6 - 0
Zengl_SRC/demos/FreePascal/15 - Video/macosx_postbuild.sh

@@ -0,0 +1,6 @@
+# copy resources
+cp ../../../bin/data/font* ../../../bin/demo15.app/Contents/Resources/
+cp ../../../bin/data/video.ogv ../../../bin/demo15.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo15_macosx.plist ../../../bin/demo15.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo15.app/Contents/Resources/demo15.icns

+ 86 - 0
Zengl_SRC/demos/FreePascal/16 - Physics/Makefile

@@ -0,0 +1,86 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src
+LIBS    = -Fu../../../lib/chipmunk/$(ARCH)-$(OS) -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/chipmunk/powerpc-$(OS) -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo16.pas
+TARGET  = demo16
+TARGETW = demo16.exe
+TARGETM = demo16
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/chipmunk/i386-linux \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/chipmunk/i386-win32 \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/chipmunk/x86_64-win64 \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 232 - 0
Zengl_SRC/demos/FreePascal/16 - Physics/demo16.pas

@@ -0,0 +1,232 @@
+program demo16;
+
+// RU: В этом файле конфигурации содержится "опция" USE_CHIPMUNK_STATIC для статической компиляции с Chipmunk
+// EN: This file contains "option" USE_CHIPMUNK_STATIC for static compilation with Chipmunk
+{$I zglCustomConfig.cfg}
+
+uses
+  {$IFDEF UNIX}
+  cthreads,
+  {$ENDIF}
+  zglChipmunk,
+  {$IFDEF USE_ZENGL_STATIC}
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_mouse,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_render_2d,
+  zgl_font,
+  zgl_text,
+  zgl_primitives_2d,
+  zgl_math_2d,
+  zgl_utils
+  {$ELSE}
+  zglHeader
+  {$ENDIF}
+  ;
+
+var
+  dirRes  : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};
+  fntMain : Byte;
+  space   : PcpSpace;
+  bCount  : Integer;
+  Bodies  : array of PcpBody;
+  Shapes  : array of PcpShape;
+
+  TimeStart: Byte;
+  TimePhisics: Byte;
+
+// RU: Добавить объект "шар"
+//     x, y - координаты центра
+//     mass - масса
+//     r    - радиус
+//     e    - коэффициент эластичности
+//     u    - коэффициент трения
+//
+// EN: Add new object "ball"
+//     x, y - coordinates
+//     mass - mass
+//     r    - radius
+//     e    - coefficient of restitution. (elasticity)
+//     u    - coefficient of friction
+procedure cpAddBall(x, y, r, mass, e, u : cpFloat);
+begin
+  INC(bCount);
+  SetLength(Bodies, bCount);
+  SetLength(Shapes, bCount);
+
+  Bodies[bCount - 1]   := cpBodyNew(mass, cpMomentForCircle(mass, 0, r, cpvzero));
+  Bodies[bCount - 1]^.p := cpv(x, y);
+  cpSpaceAddBody(space, Bodies[bCount - 1]);
+
+  Shapes[bCount - 1]   := cpCircleShapeNew(Bodies[bCount - 1], r, cpvzero);
+  Shapes[bCount - 1]^.e := e;
+  Shapes[bCount - 1]^.u := u;
+  cpSpaceAddShape( space, Shapes[ bCount - 1 ] );
+end;
+
+// RU: Добавить объект "коробка"
+//     Схож с процедурой cpAddBall по аргументам
+//     x, y - координаты центра
+//     w, h - ширина и высота
+//
+// EN: Add bew object "box"
+//     Arguments are similar to arguments of procedure cpAddBall
+//     x, y - coordinates of center
+//     w, h - width and height
+procedure cpAddBox(x, y, w, h, mass, e, u : cpFloat);
+  var
+    points : array[0..3] of cpVect;
+    f      : cpFloat;
+begin
+  INC(bCount);
+  SetLength(Bodies, bCount);
+  SetLength(Shapes, bCount);
+
+  points[0].x := - w / 2;
+  points[0].y := - h / 2;
+  points[1].x := - w / 2;
+  points[1].y := h / 2;
+  points[2].x := w / 2;
+  points[2].y := h / 2;
+  points[3].x := w / 2;
+  points[3].y := - h / 2;
+
+  f := cpMomentForPoly(mass, 4, @points[0], cpvzero);
+  Bodies[bCount - 1]   := cpBodyNew(mass, f);
+  Bodies[bCount - 1]^.p := cpv(x + w / 2, y + h / 2);
+  cpSpaceAddBody(space, Bodies[bCount - 1]);
+
+  Shapes[bCount - 1] := cpPolyShapeNew(Bodies[bCount - 1], 4, @points[0], cpvzero);
+  Shapes[bCount - 1]^.e := e;
+  Shapes[bCount - 1]^.u := u;
+  cpSpaceAddShape(space, Shapes[bCount - 1]);
+end;
+
+procedure Init;
+  var
+    staticBody : PcpBody;
+    ground     : PcpShape;
+    e, u       : cpFloat;
+begin
+  fntMain := font_LoadFromFile(dirRes + 'font.zfi');
+  setTextScale(15, fntMain);
+
+  cpInitChipmunk();
+
+  // RU: Создаем новый "мир".
+  // EN: Create new world.
+  space            := cpSpaceNew();
+  // RU: Задаем количество итераций обработки(рекомендуется 10).
+  // EN: Set count of iterations of processing(recommended is 10).
+  space^.iterations := 10;
+  space^.elasticIterations := 10;
+  // RU: Задаем силу гравитации.
+  // EN: Set the gravity.
+  space^.gravity    := cpv(1, 100);
+  // RU: Задаем коэффициент "затухания" движения объектов.
+  // EN: Set the damping for moving of objects.
+  space^.damping    := 0.99;
+
+  e := 1;
+  u := 0.9;
+  // RU: Создадим статичное "тело".
+  // EN: Create a static "body".
+  staticBody := cpBodyNew(INFINITY, INFINITY);
+  // RU: Добавим три отрезка для ограничения мира. Первый параметр - указатель на созданное тело, два последующих - координаты точек отрезка, последний - толщина отрезка.
+  // EN: Add three segments for restriction of world. First parameter - pointer of created body, next two - coordinates of segment points, the last one - width of segment.
+  ground := cpSegmentShapeNew(staticBody, cpv(5, 0), cpv(5, 590), 1);
+  ground^.e := e;
+  ground^.u := u;
+  cpSpaceAddStaticShape(space, ground );
+  ground := cpSegmentShapeNew(staticBody, cpv(795, 0), cpv(795, 590), 1);
+  ground^.e := e;
+  ground^.u := u;
+  cpSpaceAddStaticShape(space, ground);
+  ground := cpSegmentShapeNew(staticBody, cpv(0, 590), cpv(800, 590), 1);
+  ground^.e := e;
+  ground^.u := u;
+  cpSpaceAddStaticShape(space, ground);
+  // RU: Добавим треугольник.
+  // EN: Add the triangle.
+  staticBody := cpBodyNew(INFINITY, INFINITY);
+  ground := cpSegmentShapeNew(staticBody, cpv(400, 300), cpv(200, 350), 1);
+  ground^.e := e;
+  ground^.u := u;
+  cpSpaceAddStaticShape(space, ground);
+  ground := cpSegmentShapeNew(staticBody, cpv(200, 350), cpv(700, 350), 1);
+  ground^.e := e;
+  ground^.u := u;
+  cpSpaceAddStaticShape(space, ground);
+  ground := cpSegmentShapeNew(staticBody, cpv(700, 350), cpv(400, 300), 1);
+  ground^.e := e;
+  ground^.u := u;
+  cpSpaceAddStaticShape(space, ground);
+end;
+
+procedure Draw;
+begin
+//  batch2d_Begin();
+
+  // RU: Рендерим объекты указанного "мира". Второй аргумент функции отвечает за показ точек соприкосновения.
+  // EN: Render objects for specified "world". Second argument responsible for rendering of collision points.
+  cpDrawSpace(space, TRUE);
+
+  text_Draw(fntMain, 10, 5,  'FPS: ' + u_IntToStr(zgl_Get(RENDER_FPS)));
+  text_Draw(fntMain, 10, 25, 'Use your mouse: Left Click - box, Right Click - ball');
+//  batch2d_End();
+end;
+
+procedure Proc;
+begin
+  if mBClickCanClick(M_BLEFT_CLICK) Then
+    cpAddBox(mouseX - 10, mouseY - 10, 48, 32, 1, 0.5, 0.5);
+  if mBClickCanClick(M_BRIGHT_CLICK) Then
+    cpAddBall(mouseX, mouseY, 16, 1, 0.5, 0.9);
+
+  (*           код, который можно использовать, если ZenGL не скомпилированная библиотека.
+    if (mouseClickCanClick and M_BLEFT_CLICK) > 0 then
+      cpAddBox(mouse_X() - 10, mouse_Y() - 10, 48, 32, 1, 0.5, 0.5);
+  *)
+
+  key_ClearState();
+  mouse_ClearState();
+end;
+
+procedure Phisics;
+begin
+  cpSpaceStep(space, 1 / zgl_Get(RENDER_FPS));
+end;
+
+procedure Quit;
+begin
+  // RU: Очистка объектов и "мира".
+  // EN: Free objects and "world".
+  cpSpaceFreeChildren(space);
+  cpSpaceFree(space);
+end;
+
+Begin
+  randomize();
+
+  {$IFNDEF USE_ZENGL_STATIC}
+  if not zglLoad( libZenGL ) Then exit;
+  {$ENDIF}
+  {$IFNDEF USE_CHIPMUNK_STATIC}
+  if not cpLoad( libChipmunk ) Then exit;
+  {$ENDIF}
+
+  TimeStart := timer_Add(@Proc, 16, Start);
+  TimePhisics := timer_Add(@Phisics, 16, Start);
+
+  zgl_Reg(SYS_LOAD, @Init);
+  zgl_Reg(SYS_DRAW, @Draw);
+  zgl_Reg(SYS_EXIT, @Quit);
+
+  wnd_SetCaption(utf8_Copy('16 - Physics Simple'));
+
+  zgl_Init();
+End.

+ 24 - 0
Zengl_SRC/demos/FreePascal/16 - Physics/demo16_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo16</string>
+  <key>CFBundleIconFile</key>
+  <string>demo16</string>
+  <key>CFBundleName</key>
+  <string>demo16</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo16</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 5 - 0
Zengl_SRC/demos/FreePascal/16 - Physics/macosx_postbuild.sh

@@ -0,0 +1,5 @@
+# copy resources
+cp ../../../bin/data/font* ../../../bin/demo16.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo16_macosx.plist ../../../bin/demo16.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo16.app/Contents/Resources/demo16.icns

+ 86 - 0
Zengl_SRC/demos/FreePascal/17 - Menu(touch menu)/Makefile

@@ -0,0 +1,86 @@
+# Get current platform
+ifeq ($(shell uname -m), x86_64)
+  ARCH  = x86_64
+else
+  ARCH  = i386
+endif
+
+# Get current OS
+ifeq ($(shell uname), Linux)
+  OS    = linux
+else ifeq ($(shell uname), Darwin)
+  OS    = darwin
+  ARCH  = i386
+endif
+
+# Variables
+FPC     = fpc
+FLAGS   = -O3 -XsX -CX -Sd
+INCLUDE = -Fu../../../headers -Fi../../../headers -Fu../../../extra -Fu../../../src -Fu../../../srcGEGL
+LIBS    = -Fu../../../lib/chipmunk/$(ARCH)-$(OS) -Fu../../../lib/jpeg/$(ARCH)-$(OS) -Fu../../../lib/ogg/$(ARCH)-$(OS) -Fu../../../lib/theora/$(ARCH)-$(OS) -Fu../../../lib/zlib/$(ARCH)-$(OS) -Fu../../../lib/zip/$(ARCH)-$(OS)
+LIBSPPC = -Fu../../../lib/chipmunk/powerpc-$(OS) -Fu../../../lib/jpeg/powerpc-$(OS) -Fu../../../lib/ogg/powerpc-$(OS) -Fu../../../lib/theora/powerpc-$(OS) -Fu../../../lib/zlib/powerpc-$(OS) -Fu../../../lib/zip/powerpc-$(OS)
+OUTPUT  = ../../../bin/
+TMP     = ../tmp/
+UNIT    = demo17.pas
+TARGET  = demo17
+TARGETW = demo17.exe
+TARGETM = demo17
+BUNDLE  = $(OUTPUT)$(TARGETM).app
+
+# Targets
+all: clean
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT)$(ARCH)-$(OS)/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX
+	strip $(OUTPUT)$(ARCH)-$(OS)/$(TARGET) --strip-unneeded -R .comment -R .note
+
+linux32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/chipmunk/i386-linux \
+	-Fu../../../lib/jpeg/i386-linux \
+	-Fu../../../lib/ogg/i386-linux \
+	-Fu../../../lib/theora/i386-linux \
+	-Fu../../../lib/zlib/i386-linux \
+	-Fu../../../lib/zip/i386-linux \
+	-FE$(OUTPUT)i386-linux/ -FU$(TMP) $(FLAGS) -o$(TARGET) -TLINUX -Pi386 -Xd
+	strip $(OUTPUT)i386-linux/$(TARGET) --strip-unneeded -R .comment -R .note
+
+win32: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/chipmunk/i386-win32 \
+	-Fu../../../lib/jpeg/i386-win32 \
+	-Fu../../../lib/msvcrt/i386 \
+	-Fu../../../lib/ogg/i386-win32 \
+	-Fu../../../lib/theora/i386-win32 \
+	-Fu../../../lib/zlib/i386-win32 \
+	-Fu../../../lib/zip/i386-win32 \
+	-FE$(OUTPUT)i386-win32/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN32 -Pi386 -WG
+
+win64: clean
+	$(FPC) $(UNIT) $(INCLUDE) \
+	-Fu../../../lib/chipmunk/x86_64-win64 \
+	-Fu../../../lib/jpeg/x86_64-win64 \
+	-Fu../../../lib/msvcrt/x86_64 \
+	-Fu../../../lib/ogg/x86_64-win64 \
+	-Fu../../../lib/theora/x86_64-win64 \
+	-Fu../../../lib/zlib/x86_64-win64 \
+	-Fu../../../lib/zip/x86_64-win64 \
+	-FE$(OUTPUT)x86_64-win64/ -FU$(TMP) $(FLAGS) -o$(TARGETW) -TWIN64 -Px86_64 -WG
+
+macosx: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM) -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	mv $(OUTPUT)$(TARGETM) $(BUNDLE)/Contents/MacOS/
+	sh macosx_postbuild.sh
+
+macosx_uni: clean
+	rm -Rf $(BUNDLE)
+	mkdir {$(BUNDLE),$(BUNDLE)/{Contents,Contents/{MacOS,Resources,Frameworks}}}
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBS) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-386 -TDARWIN -Pi386 -k"-macosx_version_min" -k"10.4"
+	$(FPC) $(UNIT) $(INCLUDE) $(LIBSPPC) -FE$(OUTPUT) -FU$(TMP) $(FLAGS) -o$(TARGETM)-ppc -TDARWIN -Ppowerpc -k"-macosx_version_min" -k"10.4"
+	lipo -create $(OUTPUT)$(TARGETM)-ppc $(OUTPUT)$(TARGETM)-386 -output $(BUNDLE)/Contents/MacOS/$(TARGETM)
+	rm $(OUTPUT)$(TARGETM)-386 $(OUTPUT)$(TARGETM)-ppc
+	sh macosx_postbuild.sh
+
+clean:
+	rm -f *.*~
+	rm -f $(TMP)*.*

+ 141 - 0
Zengl_SRC/demos/FreePascal/17 - Menu(touch menu)/demo17.pas

@@ -0,0 +1,141 @@
+program demo17;
+
+{$I zglCustomConfig.cfg}
+
+// включить USE_MENUGUI в zgl_config
+uses
+  {$IFDEF UNIX}
+  cthreads,
+  {$ENDIF}
+  {$IFDEF USE_ZENGL_STATIC}
+  gegl_touch_menu,
+  zgl_screen,
+  zgl_window,
+  zgl_timers,
+  zgl_keyboard,
+  zgl_render_2d,
+  zgl_fx,
+  zgl_primitives_2d,
+  zgl_textures,
+  zgl_textures_png,
+  zgl_font,
+  zgl_text,
+  zgl_file,
+  zgl_types,
+  zgl_mouse,
+  gegl_draw_gui,
+
+  zgl_utils
+  {$ELSE}
+  zglHeader
+  {$ENDIF}
+  ;
+
+var
+  //  dirRes  : UTF8String {$IFNDEF MACOSX} = 'data/' {$ENDIF};             // вне демо-версий
+  dirRes  : UTF8String {$IFNDEF MACOSX} = '../data/' {$ENDIF};            // в демо-версиях!!!
+  TimeStart: Byte = 0;
+
+
+procedure Init;
+begin
+  file_SetPath('');                       // если dirRes = '../data/'   !!!!!     в демо-версиях!!!
+  // RU: Загружаем данные о шрифте.
+  // EN: Load the font.
+
+//  fntMain := font_LoadFromFile( dirRes + 'font.zfi' );
+  // RU: Если же текстуры именуются без использования маски вида "$(имя_шрифта)FontName-page$(номер).$(расширение)", то загрузку можно произвести следующим образом(для png):
+  // EN: If textures were named without special mask - "$(font_name)-page$(number).$(extension)", then use this method to load them(for png):
+  //for i := 0 to fntMain.Count.Pages - 1 do
+  //  fntMain.Pages[ i ] := tex_LoadFromFile( dirRes + 'font-page' + u_IntToStr( i ) + '.png' );
+
+  // обязательный код! Данные для отображения клавиатуры.
+  fontUse := font_LoadFromFile(dirRes + 'CalibriBold50pt.zfi');
+  JoyArrow := tex_LoadFromFile(dirRes + 'arrow.png');     // загрузили текстуру
+  tex_SetFrameSize(JoyArrow, 64, 64);                     // и разбили её на части, но в записях не будет указано количество полученных текстур
+  CreateTouchKeyboard;
+end;
+
+procedure Draw;
+  var
+    r : zglTRect;
+    s : UTF8String;
+begin
+  batch2d_Begin();
+  setTextScale(15, fontUse);
+
+  // RU: ZenGL работает исключительно с кодировкой UTF-8, поэтому весь текст должен быть в UTF-8.
+  // EN: ZenGL works only with UTF-8 encoding, so all text should be encoded with UTF-8.
+
+  text_Draw( fontUse, 400, 25, 'String with center alignment', TEXT_HALIGN_CENTER );
+
+  text_DrawEx( fontUse, 400, 65, 3, 0, 'Scaling', 255, $FFFFFF, TEXT_HALIGN_CENTER );
+
+  setTextScale(15, fontUse);
+  fx2d_SetVCA( $FF0000, $00FF00, $0000FF, $FFFFFF, 255, 255, 255, 255 );
+  text_Draw( fontUse, 400, 125, 'Gradient color for every symbol', TEXT_FX_VCA or TEXT_HALIGN_CENTER );
+
+  r.X := 0;
+  r.Y := 300 - 128;
+  r.W := 192;
+  r.H := 256;
+
+  pr2d_Rect( r.X, r.Y, r.W, r.H, $FF0000 );
+  text_DrawInRect( fontUse, r, 'Simple text rendering in rectangle' + #10 + 'Текст написанный в квадрате');
+  // для использования другой кодировки надо указать Lazarus что страница в кодировке UTF-8
+  // File setting -> encoding -> UTF-8 with BOM
+
+  r.X := 800 - 192;
+  r.Y := 300 - 128;
+  r.W := 192;
+  r.H := 256;
+  pr2d_Rect( r.X, r.Y, r.W, r.H, $FF0000 );
+  text_DrawInRect( fontUse, r, 'Text rendering using horizontal right alignment and vertical bottom alignment', TEXT_HALIGN_RIGHT or TEXT_VALIGN_BOTTOM );
+
+  r.X := 400 - 192;
+  r.Y := 300 - 128;
+  r.W := 384;
+  r.H := 256;
+  pr2d_Rect( r.X, r.Y, r.W, r.H, $FF0000 );
+  text_DrawInRect( fontUse, r, 'This text uses justify alignment and centered vertically. Text which doesn''t fit inside the rectangle will be cropped.',
+                   TEXT_HALIGN_JUSTIFY or TEXT_VALIGN_CENTER );
+
+  r.X := 400 - 320;
+  r.Y := 300 + 160;
+  r.W := 640;
+  r.H := 128;
+  pr2d_Rect( r.X, r.Y, r.W, r.H, $FF0000 );
+  text_DrawInRect( fontUse, r, 'For starting new line LF symbol can be used' + #10 + 'code of which is equal to 10 and named in Unicode as "Line Feed"',
+                   TEXT_HALIGN_CENTER or TEXT_VALIGN_CENTER );
+
+  // RU: Выводим количество FPS в правом углу, используя text_GetWidth.
+  // EN: Render FPS in the top right corner using text_GetWidth.
+  s := 'FPS: ' + u_IntToStr( zgl_Get( RENDER_FPS ) );
+  text_Draw( fontUse, 800 - text_GetWidth( fontUse, s ), 0, s );
+
+  batch2d_End();
+end;
+
+procedure Timer;
+begin
+
+  key_ClearState();
+  mouse_ClearState;
+end;
+
+begin
+  {$IFNDEF USE_ZENGL_STATIC}
+  if not zglLoad( libZenGL ) Then exit;
+  {$ENDIF}
+  randomize();
+
+  timer_Add( @Timer, 16, TimeStart, Start );
+
+  zgl_Reg( SYS_LOAD, @Init );
+  zgl_Reg( SYS_DRAW, @Draw );
+
+  wnd_SetCaption(utf8_Copy('06 - Text'));
+
+  zgl_Init();
+end.
+

+ 24 - 0
Zengl_SRC/demos/FreePascal/17 - Menu(touch menu)/demo17_macosx.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+  <key>CFBundleExecutable</key>
+  <string>demo17</string>
+  <key>CFBundleIconFile</key>
+  <string>demo17</string>
+  <key>CFBundleName</key>
+  <string>demo17</string>
+  <key>CFBundleIdentifier</key>
+  <string>zengl.demo17</string>
+  <key>CFBundlePackageType</key>
+  <string>APPL</string>
+  <key>CFBundleSignature</key>
+  <string>demo</string>
+  <key>CFBundleShortVersionString</key>
+  <string>1.0</string>
+  <key>CFBundleVersion</key>
+  <string>1</string>
+  <key>CSResourcesFileMapped</key>
+  <true/>
+</dict>
+</plist>

+ 5 - 0
Zengl_SRC/demos/FreePascal/17 - Menu(touch menu)/macosx_postbuild.sh

@@ -0,0 +1,5 @@
+# copy resources
+cp ../../../bin/data/font* ../../../bin/demo17.app/Contents/Resources/
+# make Info.plist and copy icon
+cp -f demo17_macosx.plist ../../../bin/demo17.app/Contents/Info.plist
+cp ../../../bin/data/zengl.icns ../../../bin/demo17.app/Contents/Resources/demo17.icns

+ 150 - 0
Zengl_SRC/demos/FreePascal/Makefile

@@ -0,0 +1,150 @@
+DEMO01 = "01 - Initialization/"
+DEMO02 = "02 - Resources/"
+DEMO03 = "03 - Input/"
+DEMO04 = "04 - Screen Settings/"
+DEMO05 = "05 - Primitives/"
+DEMO06 = "06 - Text/"
+DEMO07 = "07 - Sprites"
+DEMO08 = "08 - Sprite Engine/"
+DEMO09 = "09 - Sprite Engine(Classes)/"
+DEMO10 = "10 - Tiles/"
+DEMO11 = "11 - Grid/"
+DEMO12 = "12 - Render into Texture/"
+DEMO13 = "13 - Particles/"
+DEMO14 = "14 - Sound/"
+DEMO15 = "15 - Video/"
+DEMO16 = "16 - Physics/"
+DEMO17 = "17 - Menu(touch menu)"
+
+all:
+	make -C $(DEMO01)
+	make -C $(DEMO02)
+	make -C $(DEMO03)
+	make -C $(DEMO04)
+	make -C $(DEMO05)
+	make -C $(DEMO06)
+	make -C $(DEMO07)
+	make -C $(DEMO08)
+	make -C $(DEMO09)
+	make -C $(DEMO10)
+	make -C $(DEMO11)
+	make -C $(DEMO12)
+	make -C $(DEMO13)
+	make -C $(DEMO14)
+	make -C $(DEMO15)
+	make -C $(DEMO16)
+	make -C $(DEMO17)
+
+linux32:
+	make -C $(DEMO01) linux32
+	make -C $(DEMO02) linux32
+	make -C $(DEMO03) linux32
+	make -C $(DEMO04) linux32
+	make -C $(DEMO05) linux32
+	make -C $(DEMO06) linux32
+	make -C $(DEMO07) linux32
+	make -C $(DEMO08) linux32
+	make -C $(DEMO09) linux32
+	make -C $(DEMO10) linux32
+	make -C $(DEMO11) linux32
+	make -C $(DEMO12) linux32
+	make -C $(DEMO13) linux32
+	make -C $(DEMO14) linux32
+	make -C $(DEMO15) linux32
+	make -C $(DEMO16) linux32
+	make -C $(DEMO17) linux32
+
+win32:
+	make -C $(DEMO01) win32
+	make -C $(DEMO02) win32
+	make -C $(DEMO03) win32
+	make -C $(DEMO04) win32
+	make -C $(DEMO05) win32
+	make -C $(DEMO06) win32
+	make -C $(DEMO07) win32
+	make -C $(DEMO08) win32
+	make -C $(DEMO09) win32
+	make -C $(DEMO10) win32
+	make -C $(DEMO11) win32
+	make -C $(DEMO12) win32
+	make -C $(DEMO13) win32
+	make -C $(DEMO14) win32
+	make -C $(DEMO15) win32
+	make -C $(DEMO16) win32
+	make -C $(DEMO17) win32
+
+win64:
+	make -C $(DEMO01) win64
+	make -C $(DEMO02) win64
+	make -C $(DEMO03) win64
+	make -C $(DEMO04) win64
+	make -C $(DEMO05) win64
+	make -C $(DEMO06) win64
+	make -C $(DEMO07) win64
+	make -C $(DEMO08) win64
+	make -C $(DEMO09) win64
+	make -C $(DEMO10) win64
+	make -C $(DEMO11) win64
+	make -C $(DEMO12) win64
+	make -C $(DEMO13) win64
+	make -C $(DEMO14) win64
+	make -C $(DEMO15) win64
+	make -C $(DEMO16) win64
+	make -C $(DEMO17) win64
+
+macosx:
+	make -C $(DEMO01) macosx
+	make -C $(DEMO02) macosx
+	make -C $(DEMO03) macosx
+	make -C $(DEMO04) macosx
+	make -C $(DEMO05) macosx
+	make -C $(DEMO06) macosx
+	make -C $(DEMO07) macosx
+	make -C $(DEMO08) macosx
+	make -C $(DEMO09) macosx
+	make -C $(DEMO10) macosx
+	make -C $(DEMO11) macosx
+	make -C $(DEMO12) macosx
+	make -C $(DEMO13) macosx
+	make -C $(DEMO14) macosx
+	make -C $(DEMO15) macosx
+	make -C $(DEMO16) macosx
+	make -C $(DEMO17) macosx
+
+macosx_uni:
+	make -C $(DEMO01) macosx_uni
+	make -C $(DEMO02) macosx_uni
+	make -C $(DEMO03) macosx_uni
+	make -C $(DEMO04) macosx_uni
+	make -C $(DEMO05) macosx_uni
+	make -C $(DEMO06) macosx_uni
+	make -C $(DEMO07) macosx_uni
+	make -C $(DEMO08) macosx_uni
+	make -C $(DEMO09) macosx_uni
+	make -C $(DEMO10) macosx_uni
+	make -C $(DEMO11) macosx_uni
+	make -C $(DEMO12) macosx_uni
+	make -C $(DEMO13) macosx_uni
+	make -C $(DEMO14) macosx_uni
+	make -C $(DEMO15) macosx_uni
+	make -C $(DEMO16) macosx_uni
+	make -C $(DEMO17) macosx_uni
+
+clean:
+	make -C $(DEMO01) clean
+	make -C $(DEMO02) clean
+	make -C $(DEMO03) clean
+	make -C $(DEMO04) clean
+	make -C $(DEMO05) clean
+	make -C $(DEMO06) clean
+	make -C $(DEMO07) clean
+	make -C $(DEMO08) clean
+	make -C $(DEMO09) clean
+	make -C $(DEMO10) clean
+	make -C $(DEMO11) clean
+	make -C $(DEMO12) clean
+	make -C $(DEMO13) clean
+	make -C $(DEMO14) clean
+	make -C $(DEMO15) clean
+	make -C $(DEMO16) clean
+	make -C $(DEMO17) clean

+ 232 - 500
Zengl_SRC/extra/zglChipmunk.pas

@@ -76,9 +76,6 @@ uses
   MacOSAll,
   {$ENDIF}
    zgl_types,
-  zgl_log,
-  zgl_file,
-  zgl_utils,
   zgl_primitives_2d;
 
 
@@ -92,15 +89,13 @@ const
 {$IFDEF WINDOWS}
   libChipmunk = 'chipmunk.dll';
 {$ENDIF}
-{$IFDEF MACOSX}{$If (not defined(CPUi386))}
-  libChipmunk = 'libchipmunk.7.0.3.dylib';
-{$Else}
+{$IFDEF MACOSX}
   libChipmunk = 'libchipmunk.5.3.2.dylib';
-{$IfEnd}{$EndIf}
+{$ENDIF}
 
 // компиляция врутри???
 {$IF ( not DEFINED( USE_CHIPMUNK_STATIC ) ) and ( not DEFINED( USE_CHIPMUNK_LINK ) )}
-function  cpLoad( LibraryName : AnsiString ) : Boolean;
+function  cpLoad( LibraryName : AnsiString; Error : Boolean = TRUE ) : Boolean;
 procedure cpFree;
 {$IFEND}
 
@@ -788,15 +783,13 @@ const
   cpvzero : cpVect = ( x: 0; y : 0 );
   cpFalse : cpBool = FALSE;
   cpTrue  : cpBool = TRUE;
-  INFINITY                    = $1e1000;
+  INFINITY                    = 1e1000;
   CP_MAX_CONTACTS_PER_ARBITER = 6;
 
 // компиляция внутри???
 {$IF ( not DEFINED( USE_CHIPMUNK_STATIC ) ) and ( not DEFINED( USE_CHIPMUNK_LINK ) )}
 var
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpInitChipmunk : procedure; cdecl;
-  {$IfEnd}
   cpMomentForCircle : function( m : cpFloat; r1 : cpFloat; r2 : cpFloat; offset : cpVect ) : cpFloat; cdecl;
   cpMomentForSegment : function( m : cpFloat; a : cpVect; b : cpVect ) : cpFloat; cdecl;
   cpMomentForPoly : function( m : cpFloat; numVerts : Integer; verts : PcpVect; offset : cpVect ) : cpFloat; cdecl;
@@ -804,7 +797,6 @@ var
 
 // VECT
   // Returns the length of v.
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpvlength : function( v : cpVect ) : cpFloat; cdecl;
 
   // Spherical linearly interpolate between v1 and v2.
@@ -827,34 +819,27 @@ var
 // ARRAY
   cpArrayAlloc : function : PcpArray; cdecl;
   cpArrayInit : function( arr : PcpArray; size : Integer ) : PcpArray; cdecl;
-  {$IfEnd}
   cpArrayNew : function( size : Integer ) : PcpArray; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpArrayDestroy : procedure( arr : PcpArray); cdecl;
-  {$IfEnd}
   cpArrayFree : procedure( arr : PcpArray ); cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpArrayClear : procedure( arr : PcpArray ); cdecl;
-  {$IfEnd}
 
   cpArrayPush : procedure( arr : PcpArray; _object : Pointer ); cdecl;
   cpArrayPop : function( arr : PcpArray ) : Pointer; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpArrayDeleteIndex : procedure( arr : PcpArray; idx : Integer ); cdecl;
-  {$IfEnd}
   cpArrayDeleteObj : procedure( arr : PcpArray; obj : Pointer ); cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpArrayAppend : procedure( arr : PcpArray; other : PcpArray ); cdecl;
 
   cpArrayEach : procedure( arr : PcpArray; iterFunc : cpArrayIter; data : Pointer ); cdecl;
-  {$IfEnd}
   cpArrayContains : function( arr : PcpArray; ptr : Pointer ) : cpBool; cdecl;
 
 // ARBITER
   // Contacts are always allocated in groups.
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpContactInit : function( con : PcpContact; p : cpVect; n : cpVect; dist : cpFloat; hasg : cpHashValue ) : PcpContact; cdecl;
-  {$IfEnd}
+
   // Arbiters are allocated in large buffers by the space and don't require a destroy function
   cpArbiterInit : function( arb : PcpArbiter; a : PcpShape; b : PcpShape ) : PcpArbiter; cdecl;
 
@@ -869,9 +854,7 @@ var
 
   // Arbiter Helper Functions
   cpArbiterTotalImpulse : function( arb : PcpArbiter ) : cpVect; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpArbiterTotalImpulseWithFriction : function( arb : PcpArbiter ) : cpVect; cdecl;
-  {$IfEnd}
   cpArbiterIgnore : procedure( arb : PcpArbiter ); cdecl;
 
 // SHAPE
@@ -899,9 +882,8 @@ var
   cpSegmentShapeAlloc : function : PcpSegmentShape; cdecl;
   cpSegmentShapeInit : function( seg : PcpSegmentShape; body : PcpBody; a : cpVect; b : cpVect; radius : cpFloat ) : PcpSegmentShape; cdecl;
   cpSegmentShapeNew : function( body : PcpBody; a : cpVect; b : cpVect; radius : cpFloat ) : PcpShape; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpResetShapeIdCounter : procedure; cdecl;
-  {$IfEnd}
 
   cpShapeSegmentQuery : function( shape : PcpShape; a : cpVect; b : cpVect; info : PcpSegmentQueryInfo ) : cpBool; cdecl;
 
@@ -915,11 +897,9 @@ var
   cpBoxShapeNew : function( body : PcpBody; width : cpFloat; height : cpFloat ) : PcpShape; cdecl;
 
   // Check that a set of vertexes has a correct winding and that they are convex
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpPolyValidate : function( verts : PcpVect; numVerts : Integer ) : cpBool; cdecl;
 
   cpPolyShapeGetNumVerts : function( shape : PcpShape ) : Integer; cdecl;
-  {$IfEnd}
   cpPolyShapeGetVert : function( shape : PcpShape; idx : Integer ) : cpVect; cdecl;
 
 // BODY
@@ -943,16 +923,13 @@ var
 
   //  Modify the velocity of the body so that it will move to the specified absolute coordinates in the next timestep.
   // Intended for objects that are moved manually with a custom velocity integration function.
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpBodySlew : procedure( body : PcpBody; pos : cpVect; dt : cpFloat ); cdecl;
-  {$IfEnd}
 
   // Default Integration functions.
   cpBodyUpdateVelocity : procedure( body : PcpBody; gravity : cpVect; damping : cpFloat; dt : cpFloat ); cdecl;
   cpBodyUpdatePosition : procedure( body : PcpBody; dt : cpFloat ); cdecl;
 
   // Zero the forces on a body.
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpBodyResetForces : procedure( body : PcpBody ); cdecl;
   // Apply a force (in world coordinates) to a body at a point relative to the center of gravity (also in world coordinates).
   cpBodyApplyForce : procedure( body : PcpBody; f : cpVect; r : cpVect ); cdecl;
@@ -960,72 +937,61 @@ var
   // Apply a damped spring force between two bodies.
   // Warning: Large damping values can be unstable. Use a cpDampedSpring constraint for this instead.
   cpApplyDampedSpring : procedure( a : PcpBody; b : PcpBody; anchr1 : cpVect; anchr2 : cpVect; rlen : cpFloat; k : cpFloat; dmp : cpFloat; dt : cpFloat ); cdecl;
-  {$IfEnd}
 
 // CONSTRAINTS
   cpConstraintDestroy : procedure( constraint : PcpConstraint ); cdecl;
   cpConstraintFree : procedure( constraint : PcpConstraint ); cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpPinJointGetClass: function: PcpConstraintClass; cdecl;
-  {$IfEnd}
   cpPinJointAlloc : function : PcpPinJoint; cdecl;
   cpPinJointInit : function( joint : PcpPinJoint; a : PcpBody; b : PcpBody; anchr1 : cpVect; anchr2 : cpVect ) : PcpPinJoint; cdecl;
   cpPinJointNew : function( a : PcpBody; b : PcpBody; anchr1 : cpVect; anchr2 : cpVect ) : PcpConstraint; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpSlideJointGetClass: function: PcpConstraintClass; cdecl;
-  {$IfEnd}
   cpSlideJointAlloc : function : PcpSlideJoint; cdecl;
   cpSlideJointInit : function( joint : PcpSlideJoint; a : PcpBody; b : PcpBody; anchr1 : cpVect; anchr2 : cpVect; min : cpFloat; max : cpFloat ) : PcpSlideJoint; cdecl;
   cpSlideJointNew : function( a : PcpBody; b : PcpBody; anchr1 : cpVect; anchr2 : cpVect; min : cpFloat; max : cpFloat ) : PcpConstraint; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpPivotJointGetClass: function: PcpConstraintClass; cdecl;
-  {$IfEnd}
   cpPivotJointAlloc : function : PcpPivotJoint; cdecl;
   cpPivotJointInit : function( joint : PcpPivotJoint; a : PcpBody; b : PcpBody; anchr1 : cpVect; anchr2 : cpVect ) : PcpPivotJoint; cdecl;
   cpPivotJointNew : function( a : PcpBody; b : PcpBody; pivot : cpVect ) : PcpConstraint; cdecl;
   cpPivotJointNew2 : function( a : PcpBody; b : PcpBody; anchr1 : cpVect; anchr2 : cpVect ) : PcpConstraint; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpGrooveJointGetClass: function: PcpConstraintClass; cdecl;
-  {$IfEnd}
   cpGrooveJointAlloc : function : PcpGrooveJoint; cdecl;
   cpGrooveJointInit : function( joint : PcpGrooveJoint; a : PcpBody; b : PcpBody; groove_a : cpVect; groove_b : cpVect; anchr2 : cpVect ) : PcpGrooveJoint; cdecl;
   cpGrooveJointNew : function( a : PcpBody; b : PcpBody; groove_a : cpVect; groove_b : cpVect; anchr2 : cpVect ) : PcpConstraint; cdecl;
 
   cpGrooveJointSetGrooveA : procedure( constraint : PcpConstraint; value : cpVect ); cdecl;
   cpGrooveJointSetGrooveB : procedure( constraint : PcpConstraint; value : cpVect ); cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpDampedSpringGetClass: function : PcpConstraintClass; cdecl;
-  {$IfEnd}
   cpDampedSpringAlloc : function : PcpDampedSpring; cdecl;
   cpDampedSpringInit : function( joint : PcpDampedSpring; a : PcpBody; b : PcpBody; anchr1 : cpVect; anchr2 : cpVect; restLength : cpFloat; stiffness : cpFloat; damping : cpFloat ) : PcpDampedSpring; cdecl;
   cpDampedSpringNew : function( a : PcpBody; b : PcpBody; anchr1 : cpVect; anchr2 : cpVect; restLength : cpFloat; stiffness : cpFloat; damping : cpFloat ) : PcpConstraint; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpDampedRotarySpringGetClass: function : PcpConstraintClass; cdecl;
-  {$IfEnd}
   cpDampedRotarySpringAlloc : function : PcpDampedRotarySpring; cdecl;
   cpDampedRotarySpringInit : function( joint : PcpDampedRotarySpring; a : PcpBody; b : PcpBody; restAngle : cpFloat; stiffness : cpFloat; damping : cpFloat ) : PcpDampedRotarySpring; cdecl;
   cpDampedRotarySpringNew : function( a : PcpBody; b : PcpBody; restAngle : cpFloat; stiffness : cpFloat; damping : cpFloat ) : PcpConstraint; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpRotaryLimitJointGetClass: function : PcpConstraintClass; cdecl;
-  {$IfEnd}
   cpRotaryLimitJointAlloc : function : PcpRotaryLimitJoint; cdecl;
   cpRotaryLimitJointInit : function( joint : PcpRotaryLimitJoint; a : PcpBody; b : PcpBody; min : cpFloat; max : cpFloat ) : PcpRotaryLimitJoint; cdecl;
   cpRotaryLimitJointNew : function( a : PcpBody; b : PcpBody; min : cpFloat; max : cpFloat ) : PcpConstraint; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpRatchetJointGetClass: function : PcpConstraintClass; cdecl;
-  {$IfEnd}
   cpRatchetJointAlloc : function : PcpRatchetJoint; cdecl;
   cpRatchetJointInit : function( joint : PcpRatchetJoint; a : PcpBody; b : PcpBody; phase : cpFloat; ratchet : cpFloat ) : PcpRatchetJoint; cdecl;
   cpRatchetJointNew : function( a : PcpBody; b : PcpBody; phase : cpFloat; ratchet : cpFloat ) : PcpConstraint; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpGearJointGetClass: function : PcpConstraintClass; cdecl;
-  {$IfEnd}
   cpGearJointAlloc : function : PcpGearJoint; cdecl;
   cpGearJointInit : function( joint : PcpGearJoint; a : PcpBody; b : PcpBody; phase : cpFloat; ratio : cpFloat ) : PcpGearJoint; cdecl;
   cpGearJointNew : function( a : PcpBody; b : PcpBody; phase : cpFloat; ratio : cpFloat ) : PcpConstraint; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpSimpleMotorGetClass: function : PcpConstraintClass; cdecl;
-  {$IfEnd}
   cpSimpleMotorAlloc : function : PcpSimpleMotor; cdecl;
   cpSimpleMotorInit : function( joint : PcpSimpleMotor; a : PcpBody; b : PcpBody; rate : cpFloat ) : PcpSimpleMotor; cdecl;
   cpSimpleMotorNew : function( a : PcpBody; b : PcpBody; rate : cpFloat ) : PcpConstraint; cdecl;
@@ -1040,30 +1006,21 @@ var
   cpSpaceFree : procedure( space : PcpSpace ); cdecl;
 
   // Convenience function. Frees all referenced entities. (bodies, shapes and constraints)
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpSpaceFreeChildren : procedure( space : PcpSpace ); cdecl;
 
-
 // Collision handler management functions.
   cpSpaceSetDefaultCollisionHandler : procedure( space : PcpSpace; _begin : cpCollisionBeginFunc; preSolve : cpCollisionPreSolveFunc; postSolve : cpCollisionPostSolveFunc; separate : cpCollisionSeparateFunc; data : Pointer ); cdecl;
-  {$IfEnd}
   cpSpaceAddCollisionHandler : procedure( space : PcpSpace; a : cpCollisionType; b : cpCollisionType; _begin : cpCollisionBeginFunc; preSolve : cpCollisionPreSolveFunc; postSolve : cpCollisionPostSolveFunc;  separate : cpCollisionSeparateFunc; data : Pointer ); cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpSpaceRemoveCollisionHandler : procedure( space : PcpSpace; a : cpCollisionType; b : cpCollisionType ); cdecl;
-  {$IfEnd}
 
   // Add and remove entities from the system.
   cpSpaceAddShape : function( space : PcpSpace; shape : PcpShape ) : PcpShape; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpSpaceAddStaticShape : function( space : PcpSpace; shape : PcpShape ) : PcpShape; cdecl;
-  {$IfEnd}
   cpSpaceAddBody : function( space : PcpSpace; body : PcpBody ) : PcpBody; cdecl;
   cpSpaceAddConstraint : function( space : PcpSpace; constraint : PcpConstraint ) : PcpConstraint; cdecl;
 
   cpSpaceRemoveShape : procedure( space : PcpSpace; shape : PcpShape ); cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpSpaceRemoveStaticShape : procedure( space : PcpSpace; shape : PcpShape ); cdecl;
-  {$IfEnd}
   cpSpaceRemoveBody : procedure( space : PcpSpace; body : PcpBody ); cdecl;
   cpSpaceRemoveConstraint : procedure( space : PcpSpace; constraint : PcpConstraint );  cdecl;
 
@@ -1073,9 +1030,7 @@ var
 
   // Point query callback function
   cpSpacePointQuery : procedure( space : PcpSpace; point : cpVect; layers : cpLayers; group : cpGroup; func : cpSpacePointQueryFunc; data : Pointer ); cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpSpacePointQueryFirst : function( space : PcpSpace; point : cpVect; layers : cpLayers; group : cpGroup ) : PcpShape; cdecl;
-  {$IfEnd}
 
   // Segment query callback function
   cpSpaceSegmentQuery : procedure( space : PcpSpace; start : cpVect; _end : cpVect; layers : cpLayers; group : cpGroup; func : cpSpaceSegmentQueryFunc; data : Pointer ); cdecl;
@@ -1088,27 +1043,22 @@ var
   cpSpaceEachBody : procedure( space : PcpSpace; func : cpSpaceBodyIterator; data : Pointer ); cdecl;
 
   // Spatial hash management functions.
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpSpaceResizeStaticHash : procedure( space : PcpSpace; dim : cpFloat; count : Integer ); cdecl;
   cpSpaceResizeActiveHash : procedure( space : PcpSpace; dim : cpFloat; count : Integer ); cdecl;
   cpSpaceRehashStatic : procedure( space : PcpSpace ); cdecl;
 
   cpSpaceRehashShape : procedure( space : PcpSpace; shape : PcpShape ); cdecl;
-  {$IfEnd}
 
   // Update the space.
   cpSpaceStep : procedure( space : PcpSpace; dt : cpFloat ); cdecl;
 
 // HASHSET
   // Basic allocation/destruction functions.
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpHashSetDestroy : procedure( _set : PcpHashSet ); cdecl;
-  {$IfEnd}
   cpHashSetFree : procedure( _set : PcpHashSet ); cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpHashSetAlloc : function : PcpHashSet; cdecl;
   cpHashSetInit : function( _set : PcpHashSet; size : Integer; eqlFunc : cpHashSetEqlFunc; trans : cpHashSetTransFunc ) : PcpHashSet; cdecl;
-  {$IfEnd}
   cpHashSetNew : function( size : Integer; eqlFunc : cpHashSetEqlFunc; trans : cpHashSetTransFunc ) : PcpHashSet; cdecl;
 
   // Insert an element into the set, returns the element.
@@ -1128,16 +1078,14 @@ var
   cpSpaceHashAlloc : function : PcpSpaceHash; cdecl;
   cpSpaceHashInit : function( hash : PcpSpaceHash; clldim : cpFloat; cells : Integer; bbfunc : cpSpaceHashBBFunc ) : PcpSpaceHash; cdecl;
   cpSpaceHashNew : function( clldim : cpFloat; cells : Integer; bbfunc : cpSpaceHashBBFunc ) : PcpSpaceHash; cdecl;
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
+
   cpSpaceHashDestroy : procedure( hash : PcpSpaceHash ); cdecl;
   cpSpaceHashFree : procedure( hash : PcpSpaceHash ); cdecl;
-  {$IfEnd}
 
   // Resize the hashtable. (Does not rehash! You must call cpSpaceHashRehash() if needed.)
   cpSpaceHashResize : procedure( hash : PcpSpaceHash; celldim : cpFloat; numcells : Integer ); cdecl;
 
   // Add an object to the hash.
-  {$If not(defined(MACOSX) and not defined(CPUi386))}
   cpSpaceHashInsert : procedure( hash : PcpSpaceHash; obj : Pointer; id : cpHashValue; _deprecated_ignored : cpBB ); cdecl;
   // Remove an object from the hash.
   cpSpaceHashRemove : procedure( hash : PcpSpaceHash; obj : Pointer; id : cpHashValue ); cdecl;
@@ -1167,7 +1115,6 @@ var
   // which should be at least CP_MAX_CONTACTS_PER_ARBITER in length.
   // This function was very lonely in cpCollision.h :)
   cpCollideShapes : function( a : PcpShape; b : PcpShape; arr : PcpContact ) : Integer; cdecl;
-  {$IfEnd}
 {$ELSE}
   procedure cpInitChipmunk; cdecl;{$IFDEF USE_CHIPMUNK_LINK} external libChipmunk; {$ELSE} external; {$ENDIF}
   function cpMomentForCircle( m : cpFloat; r1 : cpFloat; r2 : cpFloat; offset : cpVect ) : cpFloat; cdecl;{$IFDEF USE_CHIPMUNK_LINK} external libChipmunk; {$ELSE} external; {$ENDIF}
@@ -1370,9 +1317,6 @@ function cpvrotate( v1 : cpVect; v2 : cpVect ) : cpVect;
 function cpvunrotate( v1 : cpVect; v2 : cpVect ) : cpVect;
 // Returns the squared length of v. Faster than cpvlength() when you only need to compare lengths.
 function cpvlengthsq( v : cpVect ) : cpFloat;
-{$If (defined(MACOSX) and not defined(CPUi386))}
-function cpvlength(v: cpVect): cpFloat;
-{$IfEnd}
 // Linearly interpolate between v1 and v2.
 function cpvlerp( v1 : cpVect; v2 : cpVect; t : cpFloat ) : cpVect;
 // Returns a normalized copy of v.
@@ -1547,13 +1491,6 @@ begin
   Result := cpvdot( v, v );
 end;
 
-{$If (defined(MACOSX) and not defined(CPUi386))}
-function cpvlength(v: cpVect): cpFloat;
-begin
-  Result := sqrt(cpvdot(v, v));
-end;
-{$IfEnd}
-
 function cpvlerp( v1 : cpVect; v2 : cpVect; t : cpFloat ) : cpVect;
 begin
   Result := cpvadd( cpvmult( v1, 1.0 - t ), cpvmult( v2, t ) );
@@ -1859,8 +1796,8 @@ procedure cpDrawSpace;
 begin
   if not Assigned( space ) Then exit;
 
-  cpSpaceEachBody( space.staticShapes, cpDrawShape, @cpColorStatic );
-  cpSpaceEachBody( space.activeShapes, cpDrawShape, @cpColorActive );
+  cpSpaceHashEach( space.staticShapes, cpDrawShape, @cpColorStatic );
+  cpSpaceHashEach( space.activeShapes, cpDrawShape, @cpColorActive );
 
   if DrawCollisions Then
     cpArrayEach( space.arbiters, cpDrawCollision, @cpColorCollision );
@@ -1868,22 +1805,14 @@ end;
 
 // Это компиляция внутри программы?
 {$IF ( not DEFINED( USE_CHIPMUNK_STATIC ) ) and ( not DEFINED( USE_CHIPMUNK_LINK ) )}
-function cpLoad( LibraryName : AnsiString) : Boolean;
-  function GetAddr(name: PChar): Pointer;
-  begin
-    Result := dlsym(cpLib, name);
-    if Result = nil then
-      log_Add(utf8_Copy(name + ' not loaded'))
-    else
-      log_Add(utf8_Copy('loaded ' + name));
-  end;
-
+function cpLoad( LibraryName : AnsiString; Error : Boolean = TRUE ) : Boolean;
 begin
-  {$IFDEF UNIX}{$IfNDef MACOSX}
+  Result := FALSE;
+  {$IFDEF UNIX}
   cpLib := dlopen( PAnsiChar( './' + LibraryName ), $001 );
   if not Assigned( cpLib ) Then
-  {$Else}
-  {$IfDef CPUi386}
+  {$ENDIF}
+  {$IFDEF MACOSX}
   mainBundle  := CFBundleGetMainBundle;
   tmpCFURLRef := CFBundleCopyBundleURL( mainBundle );
   tmpCFString := CFURLCopyFileSystemPath( tmpCFURLRef, kCFURLPOSIXPathStyle );
@@ -1891,415 +1820,218 @@ begin
   mainPath    := tmpPath + '/Contents/';
   LibraryName := mainPath + 'Frameworks/' + LibraryName;
   {$ENDIF}
-  {$EndIf}
-  {$EndIf}
   cpLib := dlopen( PAnsiChar( LibraryName ) {$IFDEF UNIX}, $001 {$ENDIF} );
 
   if cpLib <> {$IFDEF UNIX} nil {$ENDIF} {$IFDEF WINDOWS} 0 {$ENDIF} Then
-  begin
-    Result := TRUE;
-
-    cpInitChipmunk                    := GetAddr('cpInitChipmunk' );
-    cpMomentForCircle                 := GetAddr('cpMomentForCircle' );
-    cpMomentForSegment                := GetAddr('cpMomentForSegment' );
-    cpMomentForPoly                   := GetAddr('cpMomentForPoly' );
-    cpMomentForBox                    := GetAddr('cpMomentForBox' );
-
-//    cpvlength                         := GetAddr('cpvlength' );
-    cpvslerp                          := GetAddr('cpvslerp' );
-    cpvslerpconst                     := GetAddr('cpvslerpconst' );
-    cpvforangle                       := GetAddr('cpvforangle' );
-    cpvtoangle                        := GetAddr('cpvtoangle' );
-
-    cpBBClampVect                     := GetAddr('cpBBClampVect' );
-    cpBBWrapVect                      := GetAddr('cpBBWrapVect' );
-
-    cpArrayAlloc                      := GetAddr('cpArrayAlloc' );
-    cpArrayInit                       := GetAddr('cpArrayInit' );
-    cpArrayNew                        := GetAddr('cpArrayNew' );
-    cpArrayDestroy                    := GetAddr('cpArrayDestroy' );
-    cpArrayFree                       := GetAddr('cpArrayFree' );
-    cpArrayClear                      := GetAddr('cpArrayClear' );
-    cpArrayPush                       := GetAddr('cpArrayPush' );
-    cpArrayPop                        := GetAddr('cpArrayPop' );
-    cpArrayDeleteIndex                := GetAddr('cpArrayDeleteIndex' );
-    cpArrayDeleteObj                  := GetAddr('cpArrayDeleteObj' );
-    cpArrayAppend                     := GetAddr('cpArrayAppend' );
-    cpArrayEach                       := GetAddr('cpArrayEach' );
-    cpArrayContains                   := GetAddr('cpArrayContains' );
-
-    cpContactInit                     := GetAddr('cpContactInit' );
-    cpArbiterInit                     := GetAddr('cpArbiterInit' );
-    cpArbiterUpdate                   := GetAddr('cpArbiterUpdate' );
-    cpArbiterPreStep                  := GetAddr('cpArbiterPreStep' );
-    cpArbiterApplyCachedImpulse       := GetAddr('cpArbiterApplyCachedImpulse' );
-    cpArbiterApplyImpulse             := GetAddr('cpArbiterApplyImpulse' );
-    cpArbiterTotalImpulse             := GetAddr('cpArbiterTotalImpulse' );
-    cpArbiterTotalImpulseWithFriction := GetAddr('cpArbiterTotalImpulseWithFriction' );
-    cpArbiterIgnore                   := GetAddr('cpArbiterIgnore' );
-
-    cpShapeInit                       := GetAddr('cpShapeInit' );
-    cpShapeDestroy                    := GetAddr('cpShapeDestroy' );
-    cpShapeFree                       := GetAddr('cpShapeFree' );
-    cpShapeCacheBB                    := GetAddr('cpShapeCacheBB' );
-    cpShapePointQuery                 := GetAddr('cpShapePointQuery' );
-
-    cpCircleShapeAlloc                := GetAddr('cpCircleShapeAlloc' );
-    cpCircleShapeInit                 := GetAddr('cpCircleShapeInit' );
-    cpCircleShapeNew                  := GetAddr('cpCircleShapeNew' );
-
-    cpSegmentShapeAlloc               := GetAddr('cpSegmentShapeAlloc' );
-    cpSegmentShapeInit                := GetAddr('cpSegmentShapeInit' );
-    cpSegmentShapeNew                 := GetAddr('cpSegmentShapeNew' );
-
-    cpResetShapeIdCounter             := GetAddr('cpResetShapeIdCounter' );
-    cpShapeSegmentQuery               := GetAddr('cpShapeSegmentQuery' );
-
-    cpPolyShapeAlloc                  := GetAddr('cpPolyShapeAlloc' );
-    cpPolyShapeInit                   := GetAddr('cpPolyShapeInit' );
-    cpPolyShapeNew                    := GetAddr('cpPolyShapeNew' );
-    cpBoxShapeInit                    := GetAddr('cpBoxShapeInit' );
-    cpBoxShapeNew                     := GetAddr('cpBoxShapeNew' );
-    cpPolyValidate                    := GetAddr('cpPolyValidate' );
-    cpPolyShapeGetNumVerts            := GetAddr('cpPolyShapeGetNumVerts' );
-    cpPolyShapeGetVert                := GetAddr('cpPolyShapeGetVert' );
-
-    cpBodyAlloc                       := GetAddr('cpBodyAlloc' );
-    cpBodyInit                        := GetAddr('cpBodyInit' );
-    cpBodyNew                         := GetAddr('cpBodyNew' );
-    cpBodyDestroy                     := GetAddr('cpBodyDestroy' );
-    cpBodyFree                        := GetAddr('cpBodyFree' );
-    cpBodyActivate                    := GetAddr('cpBodyActivate' );
-    cpBodySleep                       := GetAddr('cpBodySleep' );
-    cpBodySetMass                     := GetAddr('cpBodySetMass' );
-    cpBodySetMoment                   := GetAddr('cpBodySetMoment' );
-    cpBodySetAngle                    := GetAddr('cpBodySetAngle' );
-    cpBodySlew                        := GetAddr('cpBodySlew' );
-    cpBodyUpdateVelocity              := GetAddr('cpBodyUpdateVelocity' );
-    cpBodyUpdatePosition              := GetAddr('cpBodyUpdatePosition' );
-    cpBodyResetForces                 := GetAddr('cpBodyResetForces' );
-    cpBodyApplyForce                  := GetAddr('cpBodyApplyForce' );
-    cpApplyDampedSpring               := GetAddr('cpApplyDampedSpring' );
-
-    cpConstraintDestroy               := GetAddr('cpConstraintDestroy' );
-    cpConstraintFree                  := GetAddr('cpConstraintFree' );
-    cpPinJointGetClass                := GetAddr('cpPinJointGetClass' );
-    cpPinJointAlloc                   := GetAddr('cpPinJointAlloc' );
-    cpPinJointInit                    := GetAddr('cpPinJointInit' );
-    cpPinJointNew                     := GetAddr('cpPinJointNew' );
-    cpSlideJointGetClass              := GetAddr('cpSlideJointGetClass' );
-    cpSlideJointAlloc                 := GetAddr('cpSlideJointAlloc' );
-    cpSlideJointInit                  := GetAddr('cpSlideJointInit' );
-    cpSlideJointNew                   := GetAddr('cpSlideJointNew' );
-    cpPivotJointGetClass              := GetAddr('cpPivotJointGetClass' );
-    cpPivotJointAlloc                 := GetAddr('cpPivotJointAlloc' );
-    cpPivotJointInit                  := GetAddr('cpPivotJointInit' );
-    cpPivotJointNew                   := GetAddr('cpPivotJointNew' );
-    cpPivotJointNew2                  := GetAddr('cpPivotJointNew2' );
-    cpGrooveJointGetClass             := GetAddr('cpGrooveJointGetClass' );
-    cpGrooveJointAlloc                := GetAddr('cpGrooveJointAlloc' );
-    cpGrooveJointInit                 := GetAddr('cpGrooveJointInit' );
-    cpGrooveJointNew                  := GetAddr('cpGrooveJointNew' );
-    cpGrooveJointSetGrooveA           := GetAddr('cpGrooveJointSetGrooveA' );
-    cpGrooveJointSetGrooveB           := GetAddr('cpGrooveJointSetGrooveB' );
-    cpDampedSpringGetClass            := GetAddr('cpDampedSpringGetClass' );
-    cpDampedSpringAlloc               := GetAddr('cpDampedSpringAlloc' );
-    cpDampedSpringInit                := GetAddr('cpDampedSpringInit' );
-    cpDampedSpringNew                 := GetAddr('cpDampedSpringNew' );
-    cpDampedRotarySpringGetClass      := GetAddr('cpDampedRotarySpringGetClass' );
-    cpDampedRotarySpringAlloc         := GetAddr('cpDampedRotarySpringAlloc' );
-    cpDampedRotarySpringInit          := GetAddr('cpDampedRotarySpringInit' );
-    cpDampedRotarySpringNew           := GetAddr('cpDampedRotarySpringNew' );
-    cpRotaryLimitJointGetClass        := GetAddr('cpRotaryLimitJointGetClass' );
-    cpRotaryLimitJointAlloc           := GetAddr('cpRotaryLimitJointAlloc' );
-    cpRotaryLimitJointInit            := GetAddr('cpRotaryLimitJointInit' );
-    cpRotaryLimitJointNew             := GetAddr('cpRotaryLimitJointNew' );
-    cpRatchetJointGetClass            := GetAddr('cpRatchetJointGetClass' );
-    cpRatchetJointAlloc               := GetAddr('cpRatchetJointAlloc' );
-    cpRatchetJointInit                := GetAddr('cpRatchetJointInit' );
-    cpRatchetJointNew                 := GetAddr('cpRatchetJointNew' );
-    cpGearJointGetClass               := GetAddr('cpGearJointGetClass' );
-    cpGearJointAlloc                  := GetAddr('cpGearJointAlloc' );
-    cpGearJointInit                   := GetAddr('cpGearJointInit' );
-    cpGearJointNew                    := GetAddr('cpGearJointNew' );
-    cpSimpleMotorGetClass             := GetAddr('cpSimpleMotorGetClass' );
-    cpSimpleMotorAlloc                := GetAddr('cpSimpleMotorAlloc' );
-    cpSimpleMotorInit                 := GetAddr('cpSimpleMotorInit' );
-    cpSimpleMotorNew                  := GetAddr('cpSimpleMotorNew' );
-
-    cpSpaceAlloc                      := GetAddr('cpSpaceAlloc' );
-    cpSpaceInit                       := GetAddr('cpSpaceInit' );
-    cpSpaceNew                        := GetAddr('cpSpaceNew' );
-    cpSpaceDestroy                    := GetAddr('cpSpaceDestroy' );
-    cpSpaceFree                       := GetAddr('cpSpaceFree' );
-    cpSpaceFreeChildren               := GetAddr('cpSpaceFreeChildren' );
-    cpSpaceSetDefaultCollisionHandler := GetAddr('cpSpaceSetDefaultCollisionHandler' );
-    cpSpaceAddCollisionHandler        := GetAddr('cpSpaceAddCollisionHandler' );
-    cpSpaceRemoveCollisionHandler     := GetAddr('cpSpaceRemoveCollisionHandler' );
-    cpSpaceAddShape                   := GetAddr('cpSpaceAddShape' );
-    cpSpaceAddStaticShape             := GetAddr('cpSpaceAddStaticShape' );
-    cpSpaceAddBody                    := GetAddr('cpSpaceAddBody' );
-    cpSpaceAddConstraint              := GetAddr('cpSpaceAddConstraint' );
-    cpSpaceRemoveShape                := GetAddr('cpSpaceRemoveShape' );
-    cpSpaceRemoveStaticShape          := GetAddr('cpSpaceRemoveStaticShape' );
-    cpSpaceRemoveBody                 := GetAddr('cpSpaceRemoveBody' );
-    cpSpaceRemoveConstraint           := GetAddr('cpSpaceRemoveConstraint' );
-    cpSpaceAddPostStepCallback        := GetAddr('cpSpaceAddPostStepCallback' );
-    cpSpacePointQuery                 := GetAddr('cpSpacePointQuery' );
-    cpSpacePointQueryFirst            := GetAddr('cpSpacePointQueryFirst' );
-    cpSpaceSegmentQuery               := GetAddr('cpSpaceSegmentQuery' );
-    cpSpaceSegmentQueryFirst          := GetAddr('cpSpaceSegmentQueryFirst' );
-    cpSpaceBBQuery                    := GetAddr('cpSpaceBBQuery' );
-    cpSpaceEachBody                   := GetAddr('cpSpaceEachBody' );
-    cpSpaceResizeStaticHash           := GetAddr('cpSpaceResizeStaticHash' );
-    cpSpaceResizeActiveHash           := GetAddr('cpSpaceResizeActiveHash' );
-    cpSpaceRehashStatic               := GetAddr('cpSpaceRehashStatic' );
-    cpSpaceRehashShape                := GetAddr('cpSpaceRehashShape' );
-    cpSpaceStep                       := GetAddr('cpSpaceStep' );
-
-    cpHashSetDestroy                  := GetAddr('cpHashSetDestroy' );
-    cpHashSetFree                     := GetAddr('cpHashSetFree' );
-    cpHashSetAlloc                    := GetAddr('cpHashSetAlloc' );
-    cpHashSetInit                     := GetAddr('cpHashSetInit' );
-    cpHashSetNew                      := GetAddr('cpHashSetNew' );
-    cpHashSetInsert                   := GetAddr('cpHashSetInsert' );
-    cpHashSetRemove                   := GetAddr('cpHashSetRemove' );
-    cpHashSetFind                     := GetAddr('cpHashSetFind' );
-    cpHashSetEach                     := GetAddr('cpHashSetEach' );
-    cpHashSetFilter                   := GetAddr('cpHashSetFilter' );
-
-    cpSpaceHashAlloc                  := GetAddr('cpSpaceHashAlloc' );
-    cpSpaceHashInit                   := GetAddr('cpSpaceHashInit' );
-    cpSpaceHashNew                    := GetAddr('cpSpaceHashNew' );
-    cpSpaceHashDestroy                := GetAddr('cpSpaceHashDestroy' );
-    cpSpaceHashFree                   := GetAddr('cpSpaceHashFree' );
-    cpSpaceHashResize                 := GetAddr('cpSpaceHashResize' );
-    cpSpaceHashInsert                 := GetAddr('cpSpaceHashInsert' );
-    cpSpaceHashRemove                 := GetAddr('cpSpaceHashRemove' );
-    cpSpaceHashEach                   := GetAddr('cpSpaceHashEach' );
-    cpSpaceHashRehash                 := GetAddr('cpSpaceHashRehash' );
-    cpSpaceHashRehashObject           := GetAddr('cpSpaceHashRehashObject' );
-    cpSpaceHashPointQuery             := GetAddr('cpSpaceHashPointQuery' );
-    cpSpaceHashQuery                  := GetAddr('cpSpaceHashQuery' );
-    cpSpaceHashQueryInsert            := GetAddr('cpSpaceHashQueryInsert' );
-    cpSpaceHashQueryRehash            := GetAddr('cpSpaceHashQueryRehash' );
-    cpSpaceHashSegmentQuery           := GetAddr('cpSpaceHashSegmentQuery' );
-
-    cpCollideShapes                   := GetAddr('cpCollideShapes' );
-  end else
-  begin
-    {$IFDEF UNIX}{$IfNDef MACOSX}
-    WriteLn( 'Error while loading Chipmunk' );
-    {$ENDIF}{$EndIf}
-    {$IFDEF WINDOWS}
-    MessageBoxA( 0, 'Error while loading Chipmunk', 'Error', $00000010 );
-    {$ENDIF}
-    {$IFDEF MACOSX}{$IfnDef CPUi386}
-
-    {$Else}
-    StandardAlert( kAlertNoteAlert, 'Error', 'Error while loading Chipmunk', nil, outItemHit );
-    {$ENDIF}{$EndIf}
-    Result := False;
-  end;
+    begin
+      Result := TRUE;
+
+      cpInitChipmunk := dlsym( cpLib, 'cpInitChipmunk' );
+      cpMomentForCircle := dlsym( cpLib, 'cpMomentForCircle' );
+      cpMomentForSegment := dlsym( cpLib, 'cpMomentForSegment' );
+      cpMomentForPoly := dlsym( cpLib, 'cpMomentForPoly' );
+      cpMomentForBox := dlsym( cpLib, 'cpMomentForBox' );
+
+      cpvlength := dlsym( cpLib, 'cpvlength' );
+      cpvslerp := dlsym( cpLib, 'cpvslerp' );
+      cpvslerpconst := dlsym( cpLib, 'cpvslerpconst' );
+      cpvforangle := dlsym( cpLib, 'cpvforangle' );
+      cpvtoangle := dlsym( cpLib, 'cpvtoangle' );
+
+      cpBBClampVect := dlsym( cpLib, 'cpBBClampVect' );
+      cpBBWrapVect := dlsym( cpLib, 'cpBBWrapVect' );
+
+      cpArrayAlloc := dlsym( cpLib, 'cpArrayAlloc' );
+      cpArrayInit := dlsym( cpLib, 'cpArrayInit' );
+      cpArrayNew := dlsym( cpLib, 'cpArrayNew' );
+      cpArrayDestroy := dlsym( cpLib, 'cpArrayDestroy' );
+      cpArrayFree := dlsym( cpLib, 'cpArrayFree' );
+      cpArrayClear := dlsym( cpLib, 'cpArrayClear' );
+      cpArrayPush := dlsym( cpLib, 'cpArrayPush' );
+      cpArrayPop := dlsym( cpLib, 'cpArrayPop' );
+      cpArrayDeleteIndex := dlsym( cpLib, 'cpArrayDeleteIndex' );
+      cpArrayDeleteObj := dlsym( cpLib, 'cpArrayDeleteObj' );
+      cpArrayAppend := dlsym( cpLib, 'cpArrayAppend' );
+      cpArrayEach := dlsym( cpLib, 'cpArrayEach' );
+      cpArrayContains := dlsym( cpLib, 'cpArrayContains' );
+
+      cpContactInit := dlsym( cpLib, 'cpContactInit' );
+      cpArbiterInit := dlsym( cpLib, 'cpArbiterInit' );
+      cpArbiterUpdate := dlsym( cpLib, 'cpArbiterUpdate' );
+      cpArbiterPreStep := dlsym( cpLib, 'cpArbiterPreStep' );
+      cpArbiterApplyCachedImpulse := dlsym( cpLib, 'cpArbiterApplyCachedImpulse' );
+      cpArbiterApplyImpulse := dlsym( cpLib, 'cpArbiterApplyImpulse' );
+      cpArbiterTotalImpulse := dlsym( cpLib, 'cpArbiterTotalImpulse' );
+      cpArbiterTotalImpulseWithFriction := dlsym( cpLib, 'cpArbiterTotalImpulseWithFriction' );
+      cpArbiterIgnore := dlsym( cpLib, 'cpArbiterIgnore' );
+
+      cpShapeInit := dlsym( cpLib, 'cpShapeInit' );
+      cpShapeDestroy := dlsym( cpLib, 'cpShapeDestroy' );
+      cpShapeFree := dlsym( cpLib, 'cpShapeFree' );
+      cpShapeCacheBB := dlsym( cpLib, 'cpShapeCacheBB' );
+      cpShapePointQuery := dlsym( cpLib, 'cpShapePointQuery' );
+
+      cpCircleShapeAlloc := dlsym( cpLib, 'cpCircleShapeAlloc' );
+      cpCircleShapeInit := dlsym( cpLib, 'cpCircleShapeInit' );
+      cpCircleShapeNew := dlsym( cpLib, 'cpCircleShapeNew' );
+
+      cpSegmentShapeAlloc := dlsym( cpLib, 'cpSegmentShapeAlloc' );
+      cpSegmentShapeInit := dlsym( cpLib, 'cpSegmentShapeInit' );
+      cpSegmentShapeNew := dlsym( cpLib, 'cpSegmentShapeNew' );
+
+      cpResetShapeIdCounter := dlsym( cpLib, 'cpResetShapeIdCounter' );
+      cpShapeSegmentQuery := dlsym( cpLib, 'cpShapeSegmentQuery' );
+
+      cpPolyShapeAlloc := dlsym( cpLib, 'cpPolyShapeAlloc' );
+      cpPolyShapeInit := dlsym( cpLib, 'cpPolyShapeInit' );
+      cpPolyShapeNew := dlsym( cpLib, 'cpPolyShapeNew' );
+      cpBoxShapeInit := dlsym( cpLib, 'cpBoxShapeInit' );
+      cpBoxShapeNew := dlsym( cpLib, 'cpBoxShapeNew' );
+      cpPolyValidate := dlsym( cpLib, 'cpPolyValidate' );
+      cpPolyShapeGetNumVerts := dlsym( cpLib, 'cpPolyShapeGetNumVerts' );
+      cpPolyShapeGetVert := dlsym( cpLib, 'cpPolyShapeGetVert' );
+
+      cpBodyAlloc :=  dlsym( cpLib, 'cpBodyAlloc' );
+      cpBodyInit := dlsym( cpLib, 'cpBodyInit' );
+      cpBodyNew := dlsym( cpLib, 'cpBodyNew' );
+      cpBodyDestroy := dlsym( cpLib, 'cpBodyDestroy' );
+      cpBodyFree := dlsym( cpLib, 'cpBodyFree' );
+      cpBodyActivate := dlsym( cpLib, 'cpBodyActivate' );
+      cpBodySleep := dlsym( cpLib, 'cpBodySleep' );
+      cpBodySetMass := dlsym( cpLib, 'cpBodySetMass' );
+      cpBodySetMoment := dlsym( cpLib, 'cpBodySetMoment' );
+      cpBodySetAngle := dlsym( cpLib, 'cpBodySetAngle' );
+      cpBodySlew := dlsym( cpLib, 'cpBodySlew' );
+      cpBodyUpdateVelocity := dlsym( cpLib, 'cpBodyUpdateVelocity' );
+      cpBodyUpdatePosition := dlsym( cpLib, 'cpBodyUpdatePosition' );
+      cpBodyResetForces := dlsym( cpLib, 'cpBodyResetForces' );
+      cpBodyApplyForce := dlsym( cpLib, 'cpBodyApplyForce' );
+      cpApplyDampedSpring := dlsym( cpLib, 'cpApplyDampedSpring' );
+
+      cpConstraintDestroy := dlsym( cpLib, 'cpConstraintDestroy' );
+      cpConstraintFree := dlsym( cpLib, 'cpConstraintFree' );
+      cpPinJointGetClass := dlsym( cpLib, 'cpPinJointGetClass' );
+      cpPinJointAlloc := dlsym( cpLib, 'cpPinJointAlloc' );
+      cpPinJointInit := dlsym( cpLib, 'cpPinJointInit' );
+      cpPinJointNew := dlsym( cpLib, 'cpPinJointNew' );
+      cpSlideJointGetClass := dlsym( cpLib, 'cpSlideJointGetClass' );
+      cpSlideJointAlloc := dlsym( cpLib, 'cpSlideJointAlloc' );
+      cpSlideJointInit := dlsym( cpLib, 'cpSlideJointInit' );
+      cpSlideJointNew := dlsym( cpLib, 'cpSlideJointNew' );
+      cpPivotJointGetClass := dlsym( cpLib, 'cpPivotJointGetClass' );
+      cpPivotJointAlloc := dlsym( cpLib, 'cpPivotJointAlloc' );
+      cpPivotJointInit := dlsym( cpLib, 'cpPivotJointInit' );
+      cpPivotJointNew := dlsym( cpLib, 'cpPivotJointNew' );
+      cpPivotJointNew2 := dlsym( cpLib, 'cpPivotJointNew2' );
+      cpGrooveJointGetClass := dlsym( cpLib, 'cpGrooveJointGetClass' );
+      cpGrooveJointAlloc := dlsym( cpLib, 'cpGrooveJointAlloc' );
+      cpGrooveJointInit := dlsym( cpLib, 'cpGrooveJointInit' );
+      cpGrooveJointNew := dlsym( cpLib, 'cpGrooveJointNew' );
+      cpGrooveJointSetGrooveA := dlsym( cpLib, 'cpGrooveJointSetGrooveA' );
+      cpGrooveJointSetGrooveB := dlsym( cpLib, 'cpGrooveJointSetGrooveB' );
+      cpDampedSpringGetClass := dlsym( cpLib, 'cpDampedSpringGetClass' );
+      cpDampedSpringAlloc := dlsym( cpLib, 'cpDampedSpringAlloc' );
+      cpDampedSpringInit := dlsym( cpLib, 'cpDampedSpringInit' );
+      cpDampedSpringNew := dlsym( cpLib, 'cpDampedSpringNew' );
+      cpDampedRotarySpringGetClass := dlsym( cpLib, 'cpDampedRotarySpringGetClass' );
+      cpDampedRotarySpringAlloc := dlsym( cpLib, 'cpDampedRotarySpringAlloc' );
+      cpDampedRotarySpringInit := dlsym( cpLib, 'cpDampedRotarySpringInit' );
+      cpDampedRotarySpringNew := dlsym( cpLib, 'cpDampedRotarySpringNew' );
+      cpRotaryLimitJointGetClass := dlsym( cpLib, 'cpRotaryLimitJointGetClass' );
+      cpRotaryLimitJointAlloc := dlsym( cpLib, 'cpRotaryLimitJointAlloc' );
+      cpRotaryLimitJointInit := dlsym( cpLib, 'cpRotaryLimitJointInit' );
+      cpRotaryLimitJointNew := dlsym( cpLib, 'cpRotaryLimitJointNew' );
+      cpRatchetJointGetClass := dlsym( cpLib, 'cpRatchetJointGetClass' );
+      cpRatchetJointAlloc := dlsym( cpLib, 'cpRatchetJointAlloc' );
+      cpRatchetJointInit := dlsym( cpLib, 'cpRatchetJointInit' );
+      cpRatchetJointNew := dlsym( cpLib, 'cpRatchetJointNew' );
+      cpGearJointGetClass := dlsym( cpLib, 'cpGearJointGetClass' );
+      cpGearJointAlloc := dlsym( cpLib, 'cpGearJointAlloc' );
+      cpGearJointInit := dlsym( cpLib, 'cpGearJointInit' );
+      cpGearJointNew := dlsym( cpLib, 'cpGearJointNew' );
+      cpSimpleMotorGetClass := dlsym( cpLib, 'cpSimpleMotorGetClass' );
+      cpSimpleMotorAlloc := dlsym( cpLib, 'cpSimpleMotorAlloc' );
+      cpSimpleMotorInit := dlsym( cpLib, 'cpSimpleMotorInit' );
+      cpSimpleMotorNew := dlsym( cpLib, 'cpSimpleMotorNew' );
+
+      cpSpaceAlloc := dlsym( cpLib, 'cpSpaceAlloc' );
+      cpSpaceInit := dlsym( cpLib, 'cpSpaceInit' );
+      cpSpaceNew := dlsym( cpLib, 'cpSpaceNew' );
+      cpSpaceDestroy := dlsym( cpLib, 'cpSpaceDestroy' );
+      cpSpaceFree := dlsym( cpLib, 'cpSpaceFree' );
+      cpSpaceFreeChildren := dlsym( cpLib, 'cpSpaceFreeChildren' );
+      cpSpaceSetDefaultCollisionHandler := dlsym( cpLib, 'cpSpaceSetDefaultCollisionHandler' );
+      cpSpaceAddCollisionHandler := dlsym( cpLib, 'cpSpaceAddCollisionHandler' );
+      cpSpaceRemoveCollisionHandler := dlsym( cpLib, 'cpSpaceRemoveCollisionHandler' );
+      cpSpaceAddShape := dlsym( cpLib, 'cpSpaceAddShape' );
+      cpSpaceAddStaticShape := dlsym( cpLib, 'cpSpaceAddStaticShape' );
+      cpSpaceAddBody := dlsym( cpLib, 'cpSpaceAddBody' );
+      cpSpaceAddConstraint := dlsym( cpLib, 'cpSpaceAddConstraint' );
+      cpSpaceRemoveShape := dlsym( cpLib, 'cpSpaceRemoveShape' );
+      cpSpaceRemoveStaticShape := dlsym( cpLib, 'cpSpaceRemoveStaticShape' );
+      cpSpaceRemoveBody := dlsym( cpLib, 'cpSpaceRemoveBody' );
+      cpSpaceRemoveConstraint := dlsym( cpLib, 'cpSpaceRemoveConstraint' );
+      cpSpaceAddPostStepCallback := dlsym( cpLib, 'cpSpaceAddPostStepCallback' );
+      cpSpacePointQuery := dlsym( cpLib, 'cpSpacePointQuery' );
+      cpSpacePointQueryFirst := dlsym( cpLib, 'cpSpacePointQueryFirst' );
+      cpSpaceSegmentQuery := dlsym( cpLib, 'cpSpaceSegmentQuery' );
+      cpSpaceSegmentQueryFirst := dlsym( cpLib, 'cpSpaceSegmentQueryFirst' );
+      cpSpaceBBQuery := dlsym( cpLib, 'cpSpaceBBQuery' );
+      cpSpaceEachBody := dlsym( cpLib, 'cpSpaceEachBody' );
+      cpSpaceResizeStaticHash := dlsym( cpLib, 'cpSpaceResizeStaticHash' );
+      cpSpaceResizeActiveHash := dlsym( cpLib, 'cpSpaceResizeActiveHash' );
+      cpSpaceRehashStatic := dlsym( cpLib, 'cpSpaceRehashStatic' );
+      cpSpaceRehashShape := dlsym( cpLib, 'cpSpaceRehashShape' );
+      cpSpaceStep := dlsym( cpLib, 'cpSpaceStep' );
+
+      cpHashSetDestroy := dlsym( cpLib, 'cpHashSetDestroy' );
+      cpHashSetFree := dlsym( cpLib, 'cpHashSetFree' );
+      cpHashSetAlloc := dlsym( cpLib, 'cpHashSetAlloc' );
+      cpHashSetInit := dlsym( cpLib, 'cpHashSetInit' );
+      cpHashSetNew := dlsym( cpLib, 'cpHashSetNew' );
+      cpHashSetInsert := dlsym( cpLib, 'cpHashSetInsert' );
+      cpHashSetRemove := dlsym( cpLib, 'cpHashSetRemove' );
+      cpHashSetFind := dlsym( cpLib, 'cpHashSetFind' );
+      cpHashSetEach := dlsym( cpLib, 'cpHashSetEach' );
+      cpHashSetFilter := dlsym( cpLib, 'cpHashSetFilter' );
+
+      cpSpaceHashAlloc := dlsym( cpLib, 'cpSpaceHashAlloc' );
+      cpSpaceHashInit := dlsym( cpLib, 'cpSpaceHashInit' );
+      cpSpaceHashNew := dlsym( cpLib, 'cpSpaceHashNew' );
+      cpSpaceHashDestroy := dlsym( cpLib, 'cpSpaceHashDestroy' );
+      cpSpaceHashFree := dlsym( cpLib, 'cpSpaceHashFree' );
+      cpSpaceHashResize := dlsym( cpLib, 'cpSpaceHashResize' );
+      cpSpaceHashInsert := dlsym( cpLib, 'cpSpaceHashInsert' );
+      cpSpaceHashRemove := dlsym( cpLib, 'cpSpaceHashRemove' );
+      cpSpaceHashEach := dlsym( cpLib, 'cpSpaceHashEach' );
+      cpSpaceHashRehash := dlsym( cpLib, 'cpSpaceHashRehash' );
+      cpSpaceHashRehashObject := dlsym( cpLib, 'cpSpaceHashRehashObject' );
+      cpSpaceHashPointQuery := dlsym( cpLib, 'cpSpaceHashPointQuery' );
+      cpSpaceHashQuery := dlsym( cpLib, 'cpSpaceHashQuery' );
+      cpSpaceHashQueryInsert := dlsym( cpLib, 'cpSpaceHashQueryInsert' );
+      cpSpaceHashQueryRehash := dlsym( cpLib, 'cpSpaceHashQueryRehash' );
+      cpSpaceHashSegmentQuery := dlsym( cpLib, 'cpSpaceHashSegmentQuery' );
+
+      cpCollideShapes := dlsym( cpLib, 'cpCollideShapes' );
+    end else
+      if Error Then
+        begin
+          {$IFDEF UNIX}
+          WriteLn( 'Error while loading Chipmunk' );
+          {$ENDIF}
+          {$IFDEF WINDOWS}
+          MessageBoxA( 0, 'Error while loading Chipmunk', 'Error', $00000010 );
+          {$ENDIF}
+          {$IFDEF MACOSX}
+          StandardAlert( kAlertNoteAlert, 'Error', 'Error while loading Chipmunk', nil, outItemHit );
+          {$ENDIF}
+        end;
 end;
 
 procedure cpFree;
 begin
   dlclose( cpLib );
-  cpInitChipmunk                     := nil;
-  cpMomentForCircle                  := nil;
-  cpMomentForSegment                 := nil;
-  cpMomentForPoly                    := nil;
-  cpMomentForBox                     := nil;
-
-//  cpvlength                          := nil;
-//  cpvslerp                           := nil;
-//  cpvslerpconst                      := nil;
-  cpvforangle                        := nil;
-  cpvtoangle                         := nil;
-
-  cpBBClampVect                      := nil;
-  cpBBWrapVect                       := nil;
-
-  cpArrayAlloc                       := nil;
-  cpArrayInit                        := nil;
-  cpArrayNew                         := nil;
-  cpArrayDestroy                     := nil;
-  cpArrayFree                        := nil;
-  cpArrayClear                       := nil;
-  cpArrayPush                        := nil;
-  cpArrayPop                         := nil;
-  cpArrayDeleteIndex                 := nil;
-  cpArrayDeleteObj                   := nil;
-  cpArrayAppend                      := nil;
-  cpArrayEach                        := nil;
-  cpArrayContains                    := nil;
-
-  cpContactInit                      := nil;
-  cpArbiterInit                      := nil;
-  cpArbiterUpdate                    := nil;
-  cpArbiterPreStep                   := nil;
-  cpArbiterApplyCachedImpulse        := nil;
-  cpArbiterApplyImpulse              := nil;
-  cpArbiterTotalImpulse              := nil;
-  cpArbiterTotalImpulseWithFriction  := nil;
-  cpArbiterIgnore                    := nil;
-
-  cpShapeInit                        := nil;
-  cpShapeDestroy                     := nil;
-  cpShapeFree                        := nil;
-  cpShapeCacheBB                     := nil;
-  cpShapePointQuery                  := nil;
-
-  cpCircleShapeAlloc                 := nil;
-  cpCircleShapeInit                  := nil;
-  cpCircleShapeNew                   := nil;
-
-  cpSegmentShapeAlloc                := nil;
-  cpSegmentShapeInit                 := nil;
-  cpSegmentShapeNew                  := nil;
-
-  cpResetShapeIdCounter              := nil;
-  cpShapeSegmentQuery                := nil;
-
-  cpPolyShapeAlloc                   := nil;
-  cpPolyShapeInit                    := nil;
-  cpPolyShapeNew                     := nil;
-  cpBoxShapeInit                     := nil;
-  cpBoxShapeNew                      := nil;
-  cpPolyValidate                     := nil;
-  cpPolyShapeGetNumVerts             := nil;
-  cpPolyShapeGetVert                 := nil;
-
-  cpBodyAlloc                        := nil;
-  cpBodyInit                         := nil;
-  cpBodyNew                          := nil;
-  cpBodyDestroy                      := nil;
-  cpBodyFree                         := nil;
-  cpBodyActivate                     := nil;
-  cpBodySleep                        := nil;
-  cpBodySetMass                      := nil;
-  cpBodySetMoment                    := nil;
-  cpBodySetAngle                     := nil;
-  cpBodySlew                         := nil;
-  cpBodyUpdateVelocity               := nil;
-  cpBodyUpdatePosition               := nil;
-  cpBodyResetForces                  := nil;
-  cpBodyApplyForce                   := nil;
-  cpApplyDampedSpring                := nil;
-
-  cpConstraintDestroy                := nil;
-  cpConstraintFree                   := nil;
-  cpPinJointGetClass                 := nil;
-  cpPinJointAlloc                    := nil;
-  cpPinJointInit                     := nil;
-  cpPinJointNew                      := nil;
-  cpSlideJointGetClass               := nil;
-  cpSlideJointAlloc                  := nil;
-  cpSlideJointInit                   := nil;
-  cpSlideJointNew                    := nil;
-  cpPivotJointGetClass               := nil;
-  cpPivotJointAlloc                  := nil;
-  cpPivotJointInit                   := nil;
-  cpPivotJointNew                    := nil;
-  cpPivotJointNew2                   := nil;
-  cpGrooveJointGetClass              := nil;
-  cpGrooveJointAlloc                 := nil;
-  cpGrooveJointInit                  := nil;
-  cpGrooveJointNew                   := nil;
-  cpGrooveJointSetGrooveA            := nil;
-  cpGrooveJointSetGrooveB            := nil;
-  cpDampedSpringGetClass             := nil;
-  cpDampedSpringAlloc                := nil;
-  cpDampedSpringInit                 := nil;
-  cpDampedSpringNew                  := nil;
-  cpDampedRotarySpringGetClass       := nil;
-  cpDampedRotarySpringAlloc          := nil;
-  cpDampedRotarySpringInit           := nil;
-  cpDampedRotarySpringNew            := nil;
-  cpRotaryLimitJointGetClass         := nil;
-  cpRotaryLimitJointAlloc            := nil;
-  cpRotaryLimitJointInit             := nil;
-  cpRotaryLimitJointNew              := nil;
-  cpRatchetJointGetClass             := nil;
-  cpRatchetJointAlloc                := nil;
-  cpRatchetJointInit                 := nil;
-  cpRatchetJointNew                  := nil;
-  cpGearJointGetClass                := nil;
-  cpGearJointAlloc                   := nil;
-  cpGearJointInit                    := nil;
-  cpGearJointNew                     := nil;
-  cpSimpleMotorGetClass              := nil;
-  cpSimpleMotorAlloc                 := nil;
-  cpSimpleMotorInit                  := nil;
-  cpSimpleMotorNew                   := nil;
-
-  cpSpaceAlloc                       := nil;
-  cpSpaceInit                        := nil;
-  cpSpaceNew                         := nil;
-  cpSpaceDestroy                     := nil;
-  cpSpaceFree                        := nil;
-  cpSpaceFreeChildren                := nil;
-  cpSpaceSetDefaultCollisionHandler  := nil;
-  cpSpaceAddCollisionHandler         := nil;
-  cpSpaceRemoveCollisionHandler      := nil;
-  cpSpaceAddShape                    := nil;
-  cpSpaceAddStaticShape              := nil;
-  cpSpaceAddBody                     := nil;
-  cpSpaceAddConstraint               := nil;
-  cpSpaceRemoveShape                 := nil;
-  cpSpaceRemoveStaticShape           := nil;
-  cpSpaceRemoveBody                  := nil;
-  cpSpaceRemoveConstraint            := nil;
-  cpSpaceAddPostStepCallback         := nil;
-  cpSpacePointQuery                  := nil;
-  cpSpacePointQueryFirst             := nil;
-  cpSpaceSegmentQuery                := nil;
-  cpSpaceSegmentQueryFirst           := nil;
-  cpSpaceBBQuery                     := nil;
-  cpSpaceEachBody                    := nil;
-  cpSpaceResizeStaticHash            := nil;
-  cpSpaceResizeActiveHash            := nil;
-  cpSpaceRehashStatic                := nil;
-  cpSpaceRehashShape                 := nil;
-  cpSpaceStep                        := nil;
-
-  cpHashSetDestroy                   := nil;
-  cpHashSetFree                      := nil;
-  cpHashSetAlloc                     := nil;
-  cpHashSetInit                      := nil;
-  cpHashSetNew                       := nil;
-  cpHashSetInsert                    := nil;
-  cpHashSetRemove                    := nil;
-  cpHashSetFind                      := nil;
-  cpHashSetEach                      := nil;
-  cpHashSetFilter                    := nil;
-
-  cpSpaceHashAlloc                   := nil;
-  cpSpaceHashInit                    := nil;
-  cpSpaceHashNew                     := nil;
-  cpSpaceHashDestroy                 := nil;
-  cpSpaceHashFree                    := nil;
-  cpSpaceHashResize                  := nil;
-  cpSpaceHashInsert                  := nil;
-  cpSpaceHashRemove                  := nil;
-  cpSpaceHashEach                    := nil;
-  cpSpaceHashRehash                  := nil;
-  cpSpaceHashRehashObject            := nil;
-  cpSpaceHashPointQuery              := nil;
-  cpSpaceHashQuery                   := nil;
-  cpSpaceHashQueryInsert             := nil;
-  cpSpaceHashQueryRehash             := nil;
-  cpSpaceHashSegmentQuery            := nil;
-
-  cpCollideShapes                    := nil;
 end;
-
-initialization
-//  cpLoad({$if defined(MACOSX) and not defined(CPUi386)}'/usr/local/lib/' + {$IfEnd}libChipmunk);
-
-finalization
-  cpFree;
 {$IFEND}
 
-end.
+end.

+ 3 - 1
Zengl_SRC/src/zgl_application.pas

@@ -462,8 +462,10 @@ begin
     mouseX := xmouse;
     mouseY := ymouse;
   end;  
-
+{$IfDef USE_MENUGUI}
   key_ClearState;
+{$Endif} 
+
 {$IfNDef USE_INIT_HANDLE}
 {$IFDEF USE_X11}
   app_ProcessMessages();