Карта сайта Kansoftware
НОВОСТИУСЛУГИРЕШЕНИЯКОНТАКТЫ
KANSoftWare

Использование PascalScript в LazCAD: особенности работы с обработчиками событий в GUI на Linux и Windows

Delphi , Программа и Интерфейс , Приложение своё

Проблемы и решения при использовании PascalScript в 64-битных приложениях на Delphi/Lazarus

Введение

PascalScript — это мощный движок для выполнения скриптов на языке Pascal, который часто используется в таких проектах, как LazCAD, для обеспечения гибкости и расширяемости. Однако при переходе на 64-битные платформы многие разработчики сталкиваются с проблемами, особенно при работе с обработчиками событий GUI. В этой статье мы рассмотрим причины этих проблем и предложим несколько решений.

Основная проблема: обработчики событий в 64-битных приложениях

Как отмечают пользователи на форумах (например, форум Lazarus), PascalScript корректно работает в 32-битных приложениях, но вызывает проблемы в 64-битных, особенно при обработке событий GUI, таких как OnClick.

Пример кода, который работает в 32-битном режиме, но не работает в 64-битном:

var 
  Form1: TForm;
  Button1: TButton;
  Memo1: TMemo;

procedure OnButton1Click(Sender: TObject);
begin
  Memo1.Text := 'Button1Click';
end;

begin
  Form1 := TForm.Create(nil);
  Button1 := TButton.Create(Form1);
  Button1.Parent := Form1;
  Button1.OnClick := @OnButton1Click;
  Memo1 := TMemo.Create(Form1);
  Memo1.Top := 50;
  Memo1.Parent := Form1;
  Form1.Show;
end.

Причины проблемы

Основная причина кроется в различиях между 32-битными и 64-битными указателями:

  1. PascalScript использует 32-битные указатели на методы внутри, что вызывает проблемы при работе в 64-битном режиме
  2. Разные соглашения о вызовах (calling conventions) между архитектурами
  3. Различное размещение параметров в регистрах и стеке

Как отмечает Martin_fr, скриптовый движок должен самостоятельно строить стек вызовов с использованием ассемблерного кода, что усложняет поддержку разных архитектур.

Решение 1: Использование 32-битного режима

Самый простой вариант — продолжать использовать 32-битную версию приложения:

// В коде проекта Lazarus:
{$IFDEF CPU32}
  // Код для 32-битной версии
{$ELSE}
  // Код для 64-битной версии или сообщение об ограничениях
{$ENDIF}

Это решение подходит, если вам не требуется использовать преимущества 64-битных систем.

Решение 2: Альтернативный механизм регистрации обработчиков

PascalScript предоставляет альтернативный механизм регистрации методов через RegisterMethodName и RegisterPropertyNameHelper. Эти методы получают параметры через объект TPSStack, что позволяет избежать проблем с соглашениями о вызовах.

Пример:

// Регистрация метода в скриптовом движке
procedure RegisterMyMethods(Exec: TPSExec);
begin
  Exec.RegisterMethodName('OnButtonClick', @ScriptButtonClick);
end;

// Обработчик в основном приложении
procedure ScriptButtonClick(Sender: TPSExec; Caller: TPSExec; Proc: TPSExternalProcRec; Global, Stack: TPSStack);
begin
  // Обработка события из скрипта
end;

Решение 3: Модификация PascalScript для 64-битных систем

Для опытных разработчиков возможно модифицировать исходный код PascalScript. Основные изменения должны касаться:

  1. Файлов с ассемблерным кодом для разных архитектур
  2. Механизма вызова методов и обработки указателей
  3. Поддержки 64-битных соглашений о вызовах

Как отмечает PascalDragon, в FPC 3.2.2+ доступен API для работы с RTTI, который может упростить эту задачу.

Решение 4: Использование обходных путей в GUI

LV предлагает альтернативный подход — создание GUI на стороне основного приложения, а не в скрипте:

// Основное приложение создает форму и элементы управления
procedure TMainForm.CreateScriptGUI;
begin
  ScriptForm := TForm.Create(nil);
  ScriptButton := TButton.Create(ScriptForm);
  ScriptButton.OnClick := MainButtonClick; // Обработчик в основном приложении
  // ...
end;

// Обработчик в основном приложении вызывает скрипт
procedure TMainForm.MainButtonClick(Sender: TObject);
begin
  ScriptExec.RunScript('OnButtonClick');
end;

Решение 5: Переход на другие скриптовые движки

Если модификация PascalScript слишком сложна, можно рассмотреть альтернативы:

  1. Lua (через Lua4Lazarus)
  2. DWScript
  3. RemObjects Pascal Script

Однако, как отмечает maurog, PascalScript имеет преимущества: - Не требует внешних DLL - Имеет встроенную IDE с отладчиком - Использует знакомый синтаксис Pascal

Практический пример: работающее решение для 64-битных систем

Вот пример кода, который работает в 64-битных приложениях, используя механизм обратных вызовов:

unit ScriptEvents;

interface

uses
  Classes, SysUtils, uPSComponent, uPSRuntime, uPSUtils;

type
  TScriptEventManager = class
  private
    FScript: TPSScript;
    FEventHandlers: TStringList;
  public
    constructor Create(AScript: TPSScript);
    destructor Destroy; override;
    procedure RegisterEvent(const EventName: string; Handler: TMethod);
    procedure ExecuteEvent(const EventName: string; Sender: TObject);
  end;

implementation

constructor TScriptEventManager.Create(AScript: TPSScript);
begin
  inherited Create;
  FScript := AScript;
  FEventHandlers := TStringList.Create;
end;

destructor TScriptEventManager.Destroy;
begin
  FEventHandlers.Free;
  inherited;
end;

procedure TScriptEventManager.RegisterEvent(const EventName: string; Handler: TMethod);
begin
  FEventHandlers.AddObject(EventName, TObject(Handler.Code));
end;

procedure TScriptEventManager.ExecuteEvent(const EventName: string; Sender: TObject);
var
  idx: Integer;
  Proc: TPSInternalProcRec;
begin
  idx := FEventHandlers.IndexOf(EventName);
  if idx >= 0 then
  begin
    Proc := FScript.GetProcMethod(IntToStr(PtrInt(FEventHandlers.Objects[idx])));
    if Proc <> nil then
    begin
      FScript.SetVarToInstance('Sender', Sender);
      FScript.ExecuteFunction([], Proc);
    end;
  end;
end;

end.

Заключение

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

Для большинства случаев рекомендуется: 1. Использовать 32-битную версию, если возможно 2. Или реализовать GUI в основном приложении, вызывая скрипты для обработки событий 3. Для сложных проектов — рассмотреть модификацию PascalScript или переход на альтернативные движки

Как отмечают участники обсуждения, Pascal остается отличным выбором для скриптования благодаря своей надежности и удобству, а проблемы 64-битной совместимости могут быть решены с некоторыми усилиями.

Создано по материалам из источника по ссылке.

Контекст описывает проблемы и решения при использовании PascalScript в 64-битных приложениях на Delphi/Lazarus, включая обработчики событий GUI и альтернативные подходы.


Комментарии и вопросы

Получайте свежие новости и обновления по Object Pascal, Delphi и Lazarus прямо в свой смартфон. Подпишитесь на наш Telegram-канал delphi_kansoftware и будьте в курсе последних тенденций в разработке под Linux, Windows, Android и iOS




Материалы статей собраны из открытых источников, владелец сайта не претендует на авторство. Там где авторство установить не удалось, материал подаётся без имени автора. В случае если Вы считаете, что Ваши права нарушены, пожалуйста, свяжитесь с владельцем сайта.


:: Главная :: Приложение своё ::


реклама


©KANSoftWare (разработка программного обеспечения, создание программ, создание интерактивных сайтов), 2007
Top.Mail.Ru

Время компиляции файла: 2024-12-22 20:14:06
2025-07-29 06:08:04/0.0067970752716064/0