Главная XFuncs smartGC InsiderTools Скачать Tutorials Купить Письма
 
 
Документация

Обзор
Документация

Пробная версия


Библиотека XFuncs позволяет использовать внешние скрипты, полностью совместимые с языком Xbase++. Вы можете вызвать из приложения функции описанные в скриптах так, как если бы они были включены в состав .exe файла. Так же все функции вашего приложения доступны для вызова из скриптов.

Содержание

Инициализация

Как определить внешнюю функцию
Расширение файлов для скрипов
Как вызвать функцию из скрипта

Ручной вызов
Как подменить функцию приложения функцией из скрипта
Значение функции MAIN() в скрипте
Как xFuncs ищет файл скрипта (.prg)

Как xFuncs ищет заголовочный файл (.ch)

Список переменных и методов объекта xFuncs()
Что такое ULink?
Как установить ULink
Известные проблемы

XFuncs против AXP: кто лучше?


вы можете вызывать скрипты из приложения, вызывать приложение из скриптов
или вызывать скрипты из скриптов


Инициализация библиотеки XFuncs

Вставьте следующую строку где-нибудь в начале вашей программы:

xFuncs():install([filepath][,par1..parN])

filepath - путь где располагаются скрипты. По-умолчанию, это текущий путь на момент вызова ::install(). Это значение хранится в xFuncs():rootPath.

par1..parN - параметры для автоматически вызываемой скрипт-функции start(). Вы можете создать файл скрипта (start.prg) с определенной функцией start() (или Main()) и эта функция будет автоматически вызываться после инициализации XFuncs.


Как определить внешнюю функцию

  • Первый случай: требуемая функция никогда не вызывается прямо из приложения, только из макроподстановки.
    (Например, если макро хранятся в базе данных и выполняются в зависимости от ситуации)

    В этом случае специального объявления не требуется.

  • Второй случай: требуемая функция вызывается из приложения и для сборки используется ULINK.

ULink это надстройка над ALink. Он автоматически создает тела для вызовов внешних функций. подробнее>

В этом случае специального объявления не требуется.

  • Третий случай: требуемая функция вызывается прямо из программы и ULINK не используется.

В этом случае требуется объявить требуемую функции командой XFUNC <funcname>[(pars..)]:

#include "xfuncs.ch"

XFUNC myUdf
XFUNC myUdf2()
XFUNC myUdf3(p1,p2)
 

Расширение файлов для скриптов

По умолчанию, расширение для скриптов ".prg". Чтобы изменить это значение, например, на ".udf" сделайте:

xFuncs():fileExt:=".udf"



Как вызвать функцию из скрипта

Чтобы вызвать функцию из скрипта, просто вызовите ее. Этот вызов полностью совпадает с вызовом обычной функции из приложения. Все оставшуюся работу по поиску файла скрипта, его компиляции и вызова, XFuncs сделает самостоятельно.

Например, если вы определили внешнюю функцию MyUdfFunc в файле MyUdfFunc.prg, просто наберите:

   MyUdfFunc()

Внимание: функция Main() имеет специальное значение. подробнее>


Ручной вызов скрипта

Чтобы откомпилировать и запустить внешнюю функцию, вызовите:

xFuncs():run(funcName,par1,..parN)-> retVal

funcName - имя внешней функции
par1..parN - параметры для вызываемой функции
retVal - возвращаемое значение вызываемой функции

Следующий пример вызывает внешнюю функции с параметрами, переданными в виде массива:

xFuncs():runA(funcName,parA)-> retVal

funcName - имя внешней функции
parA- массив параметров
retVal - возвращаемое значение вызываемой функции

Внимание: если программа имеет встроенные функции с именами такими же как имена в выполняемом скрипт файле, эти функции будут заменены на функции из скрипта. Последующие вызовы этих функций будут переназначены на соответствующие внешние функции.

 

Как подменить функцию приложения функцией из скрипта

Иногда может быть очень полезно заменить функцию встроенную в приложение на функцию из скрипта.
Это возможно двумя способами: сделать встроенную функцию неопределенной, или перегрузить ее внешней функцией при загрузке скрипта в память.

  • Эта команда делает встроенную функцию неопределенной:

    xFuncs():undefineFunc(funcName)

    При следующем вызове funcName будет автоматически вызвана внешняя функция с таким же именем.

  • Что бы загрузить скрипт с нужной функцией в память, сделайте:

    xFuncs():load(funcName|scriptFilename)

Значение функции MAIN() в скрипте

Функция Main() имеет специальное значение в файле скрипта. Когда вы пытаетесь вызвать функцию с именем, совпадающим с именем файла скрипта, но функция с таким именем не опрелена, а функция Main() пределена, то будет вызвана Main(). Другими словами, вы можете вызывать функцию Main() просто вызовом функции с таким же именем как имя файла скрипта.

Например, если MyUdf.prg не содержит функцию MyUdf(), но содержит Main(), то если вы вызовите MyUdf(), будет вызвана Main().


Как XFuncs ищет файл скрипта (.prg)


XFuncs ищет файл скрипта по имени вызываемой функции, в директории и поддиректориях пути, определенного в xFuncs():rootPath.

Например, если вызывается функция MyUdfFunc, файл MyUdfFunc.prg будет искаться в директории и поддиректориях ::rootPath.

Внимание: поддиректории проверяются в алфавитном порядке.


Как XFuncs ищет заголовочный файл (.ch)

XFuncs ищет заголовочный файл в следующем порядке:

  • сначала в директории, где находится вызываемой файл скриптов
  • ::rootPath+"INCLUDE\"
  • ::rootPath+"CH\"
  • ::rootPath
  • и в содержимом SET INCLUDE=


Список переменных и методов объекта xFuncs()

xFuncs() это специальный объект для управления библиотекой xFuncs.

::install(path)

Инициализация xFuncs и установка корневой директории скриптов (::rootPath).

::rootPath

Корневая директория скриптов. XFuncs ищет файл скрипта по имени вызываемой функции, в директории и поддиректориях пути, определенного в этой переменной .

::fileExt

Эта переменная содержит расширение для файлов со скриптами. По умолчанию, это ".prg".

::run(funcname[,par1..parN]) -> результат выполнения функции
::runA(funcname[,parA]) -> результат выполнения функции

Ручной вызов внешней функции.

::load(funcname|scriptname)

Ручная загрузка скрипта в память. Также, все встроенные в приложение функции с именами, совпадающими с именами функций из скрипта, будут заменены.

::editor

Переменная, определяющая редактор скрипта. Если вы используете внешний редактор, укажите имя файла этого редактора в ::editor. Для вызова встроенного (собственного) редактора, определите блок кода, редактирующий указанный скрипт (первый параметр блока кода -- имя файла для редактирования). Значение по умолчанию "notepad.exe".

::edit(funcname|scriptname)

Вызвать редактор для скрипта или внешней функции.

::getFilename(funcname) -> script filename

Возвращает полное имя файла скрипта, содержащего указанную функцию.

::undefineFunc(funcname)

Отменяет любую встроенную в приложение функцию. Следующий вызов этой функции вызовет внешнюю функцию или, если ее нет, сгенерирует стандартную ошибку "Функция не определена".

::redefineFunc(funcnameFrom,funcnameTo)

Подменяет (заменяет) одну функцию на другую. Следующий вызов funcnameFrom вызовет funcnameTo.

::restoreFunc(funcname)

Восстанавливает статус функции funcname, если она была отменена или подменена.



Что такое ULink?

ULink это надстройка над ALink. В отличии от Clipper, Xbase++ не позволяет вызывать неопределенные функции. Хотя существует специальный ключ для ALink (/force:unresolved) для создания файла приложения даже при неопределенных функциях, вызов такой фунции приведет к фатальной ошибке. В Clipper же просто появится ошибка "Функция не определена".

Главной задачей Ulink является имитация такого поведения Clipper в среде Alaska Xbase++. ULink вызывает ALink, анализирует результат и, если обнаружена неопределенные функции, создает файл unres.prg, компилирует его, добавляет его в список линковки и перезапускает ALink.


Как установить ULink?

Установка ULink очень проста. Загляните в ваш файл .xpj (обычно project.xpj) и замените:

[PROJECT]
..
LINKER=ALINK.EXE


на:

[PROJECT]
..
LINKER=ULINK.EXE



Известные проблемы

В компиляторе:

  • Присвоение = еще не работает. Для присвоений всегда используйте := вместо =.

В препроцессоре:

  • Не поддерживаются вложенные необязательные маркеры [].
  • Маркеры повторного присвоения не поддерживаются.

При запуске:

  • <threadObject>:start("funcname") может не работать, если funcname находится в скрипте. Пожалуйста, определите эту функцию командой XFUNC <funcname> или используйте блок кода.


XFuncs против AXP: кто лучше?

В состав профессиональной версии Xbase++ входит библиотека Active Xbase Page или AXP. Эта библиотека так же позволяет выполнять внешний код, совместимый с Xbase++. Однако, главной задачей AXP, как отмечается в документации, является "легкое заполнение файлов документов динамическим содержимым". Другими словами, скрипты AXP это своеобразные программируемые шаблоны текстовых файлов (таких как HTML, rtf, xml и др.).

Библиотека XFuncs расширяет возможности Xbase++ с другой стороны, она позволяет создавать функции и классы, видимые из главного приложения. Внешние функции и классы, определенные в скриптах абсолютно равнозначны функциям и классам содержащимся в приложении.

Из этого сравнения видно, что XFuncs и AXP не исключают друг друга, а взаимодополняют в соответствущих областях.

С точки зрения полноты реализации языка Xbase++, библиотека XFuncs значительно опережает AXP. XFuncs позволяет создавать функции и классы, поддерживат препроцессор, не требует указания имени файла со скриптом.


 

 

©2006 Eleus Software

 

 

Hosted by uCoz