Как выставить "нативные функции" для Javascript на веб-странице, используя Chromium и Delphi 6? - PullRequest
15 голосов
/ 01 августа 2011

Я успешно внедрил Chromium в мои проекты Delphi 6 с помощью Delphi Chromium Embedded .Теперь я хочу иметь возможность выполнять код Javascript и возвращать результаты в мое приложение Delphi.Мой текущий метод заключается в вызове ExecuteJavascript () и использовании элемента DOM, в который вызов Javascript записывает свои результаты, и опроса этого элемента в методе TTimer из Delphi для получения результатов.Тем не менее, я читал об использовании нативных функций и расширений V8, чтобы вместо вызова Javascript вызывать мой код Delphi в качестве способа получения результатов:

http://magpcss.org/ceforum/viewtopic.php?f=7&t=180

Я бы хотелчтобы попробовать это, я также хотел бы знать, как подключить прослушиватели событий на основе Delphi к элементам DOM на веб-странице (onblur, onmousedown и т. д.).Я ищу образцы, которые бы показали мне, как сделать эти две вещи, если кто-нибудь знает, где их найти.

1 Ответ

14 голосов
/ 01 августа 2011

Присоединить слушателей довольно легко (только в старых версиях CEF):

procedure MouseDownCallback(const Event: ICefDomEvent);
begin
  ShowMessage('Mouse down on '+Event.Target.Name);
end;

procedure AttachMouseDownListenerProc(const Doc: ICefDomDocument);
begin
  Doc.Body.AddEventListenerProc('mousedown', True, MouseDownCallback);
end;

procedure TMainForm.Button1Click(Sender: TObject);
begin
  ChromiumComponent.Browser.MainFrame.VisitDomProc(AttachMouseDownListenerProc);
end;

Относительно расширенных функций для непосредственного получения результатов JavaScript: транк не содержит их (пока?). Кажется, в процессе работы.

Редактировать

Избавление от опроса с помощью расширений :

Ваш код JavaScript действительно может перезвонить в ваш код Delphi с помощью расширений. Кроме того, вы можете отправлять значения из JavaScript в Delphi - это можно использовать для передачи результатов без необходимости опроса.

Сначала в вашем разделе initialization зарегистрируйте расширение, которое позже создаст объект JavaScript для использования при обратном вызове:

procedure RegisterExtension;
var
  Code:string;
begin

  Code :=
   'var cef;'+
   'if (!cef)'+
   '  cef = {};'+
   'if (!cef.test)'+
   '  cef.test = {};'+
   '(function() {'+
   '  cef.test.__defineGetter__(''test_param'', function() {'+
   '    native function GetTestParam();'+
   '    return GetTestParam();'+
   '  });'+
   '  cef.test.__defineSetter__(''test_param'', function(b) {'+
   '    native function SetTestParam();'+
   '    if(b) SetTestParam(b);'+
   '  });'+
   '  cef.test.test_object = function() {'+
   '    native function GetTestObject();'+
   '    return GetTestObject();'+
   '  };'+
   '})();';

  CefRegisterExtension('example/v8', Code, TMyHandler.Create as ICefv8Handler);
end;

initialization
  RegisterExtension;

TMyHandler s Execute будет вызван позже. TMyHandler определяется как

TMyHandler = class(TCefv8HandlerOwn)
protected
  function Execute(const name: ustring; const obj: ICefv8Value;
    const arguments: TCefv8ValueArray; var retval: ICefv8Value;
    var exception: ustring): Boolean; override;
end;

Реализация для демонстрационных целей пока проста:

function TMyHandler.Execute(const name: ustring; const obj: ICefv8Value; const arguments: TCefv8ValueArray; var retval: ICefv8Value; var exception: ustring): Boolean;
begin
  ShowMessage('Execute!');
end;

Теперь, чтобы протестировать вызов в Delphi из JavaScript, просто выполните:

ChromiumComponent.Browser.MainFrame.ExecuteJavaScript('cef.test.test_object().GetMessage();', 'about:blank', 0);

Это должно отобразить окно с сообщением «Выполнить!».

Я вытащил демонстрационный скрипт из примера с именем cefclient , который вы можете найти в папке \ demos \ cefclient в корневом каталоге компонентов. Пример кода расширения немного скрыт и смешан с другим демонстрационным кодом. Но особый интерес для нас представляет реализация TExtension.Execute (эквивалент моей TMyHandler.Execute). Там вы можете найти, как определить, какая функция вызывается и как передавать параметры. ( Ссылка на код. )

...