Files
lazarus-ccr/components/geckoport/version2/Components/GeckoBrowser.pas

2350 lines
69 KiB
ObjectPascal
Raw Normal View History

(* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is GeckoComponents for Delphi.
*
* The Initial Developer of the Original Code is Takanori Ito.
* Portions created by the Initial Developer are Copyright (C) 2003
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** *)
unit GeckoBrowser;
{$MACRO on}
{$IFDEF Windows}
{$DEFINE extdecl:=stdcall}
{$ELSE Windows}
{$DEFINE extdecl:=cdecl}
{$ENDIF}
{$IFNDEF FPC_HAS_CONSTREF}
{$DEFINE constref:=const}
{$ENDIF}
{$IFDEF LCLCocoa}
{$MODESWITCH ObjectiveC1}
{$ENDIF}
interface
uses
LclIntf, LMessages, LclType, LResources, Graphics,
SysUtils, Classes, Controls, nsXPCOM,
nsGeckoStrings, nsTypes, CallbackInterfaces, nsXPCOMGlue, BrowserSupports,
nsXPCOM_std19, GeckoPromptService
{$IFDEF LCLCarbon}, CarbonPrivate {$ENDIF}
{$IFDEF LCLCocoa}, CocoaPrivate, CocoaAll, CocoaUtils {$ENDIF}
{$IFDEF LCLGtk2}, gtk2,
ExtCtrls {This is temporal for TTimer needed for event pooling forced}
{$ENDIF}
;
resourcestring
SGeckoBrowserInitError = 'Failed to initialize TGeckoBrowser.';
SGeckoBrowserCannotGoBack = 'Failed to go back history.';
SGeckoBrowserCannotGoForward = 'Failed to go forward history.';
SGeckoBrowserLoadURIError = 'Failed to load URI ''%s.'' ';
SGeckoBrowserCannotReload = 'Failed to reload page.';
const
LOAD_FLAGS_NONE = 0;
LOAD_FLAGS_IS_REFRESH = 16;
LOAD_FLAGS_IS_LINK = 32;
LOAD_FLAGS_BYPASS_HISTORY = 64;
LOAD_FLAGS_REPLACE_HISTORY = 128;
LOAD_FLAGS_BYPASS_CACHE = 256;
LOAD_FLAGS_BYPASS_PROXY = 512;
LOAD_FLAGS_CHARSET_CHANGE = 1024;
{$IFDEF LCL}
const
WM_GETDLGCODE = LM_GETDLGCODE;
WM_NEXTDLGCTL = $0028;
WM_ERASEBKGND = LM_ERASEBKGND;
WM_SHOWWINDOW = LM_SHOWWINDOW;
E_FAIL = HRESULT($80004005);
type
TMessage = TLMessage;
TWMGetDlgCode = TLMNoParams;
{$ENDIF}
type
//TCtxMenuInfo = BrowserSupports.TCtxMenuInfo;
//TCtxMenuFlags = BrowserSupports.TCtxMenuFlags;
TGeckoDOMEventType = (
etNone,
etEvent,
etCustomEvent,
etUIEvent,
etMouseEvent,
etStorageEvent
);
TGeckoDOMEvent = record
Name: String;
EventType: TGeckoDOMEventType;
event: nsIDOMEvent;
end;
TGeckoDOMEventRegister = record
Name: String;
eventType: TGeckoDOMEventType;
propertyName: String;
end;
TGeckoDOMEventRegisterArray = array [0..99] of TGeckoDOMEventRegister;
PGeckoDOMEventRegisterArray = ^TGeckoDOMEventRegisterArray;
TCustomGeckoBrowser = class;
TCustomGeckoBrowserChrome = class;
TCustomGeckoBrowserListener = class;
TGeckoBrowser = class;
TGeckoBrowserChrome = class;
TGeckoBrowserListener = class;
TCtxMenuInfo = class;
EGeckoBrowserError = class(EGeckoError)
end;
EGeckoBrowserNavigationError = class(EGeckoBrowserError)
end;
{$PUSH}{$HINTS OFF} //Redefinition to expose the interface
IDirectoryServiceProvider=nsXPCOMGlue.IDirectoryServiceProvider;
{$POP}
TGeckoBrowserContextMenu = procedure (Sender: TObject; aInfo: TCtxMenuInfo) of object;
TGeckoBrowserStatusChange = procedure (Sender: TObject; aMessage: WideString) of object;
TGeckoBrowserNewWindow = procedure (Sender: TObject; aChromeFlags: Longword; var newWindow: TCustomGeckoBrowser) of object;
TGeckoBrowserProgressChange = procedure (Sender: TObject; Progress: Integer; ProgressMax: Integer) of object;
TGeckoBrowserTitleChange = procedure (Sender: TObject; const Text: WideString) of object;
TGeckoBrowserVisibleChange = procedure (Sender: TObject; Vislble: Bool) of object;
TGeckoBrowserLocationChange = procedure (Sender: TObject; const uri: AnsiString) of object;
TGeckoBrowserDOMEventHandler = procedure (Sender: TObject; aEvent:TGeckoDOMEvent) of object;
TGeckoBrowserHistoryMove = procedure (Sender: TObject; aURI: nsIURI; out aContinue: LongBool; var Handled: Boolean) of object;
TGeckoBrowserHistoryGoTo = procedure (Sender: TObject; aIndex: Longint; aURI: nsIURI; out aContinue: LongBool; var Handled: Boolean) of object;
TGeckoBrowserDirectoryService = procedure (Sender: TObject; const aDirectoryService: IDirectoryServiceProvider) of object;
TGeckoBrowserHisoty = record
URI: AnsiString;
Title: WideString;
IsSubFrame: Boolean;
end;
//TODO 2 -cTCustomGeckoBrowser: DocShell �v��p�e�B���lj�
{ TCustomGeckoBrowser }
TCustomGeckoBrowser = class(TCustomControl,
IGeckoCreateWindowTarget)
private
FWebBrowser: nsIWebBrowser;
FListeners: TCustomGeckoBrowserListener;
FChrome: TCustomGeckoBrowserChrome;
// �C�x���g
// nsIWebProgressListener
FOnStatusChange: TGeckoBrowserStatusChange;
FOnProgressChange: TGeckoBrowserProgressChange;
FOnLocationChange: TGeckoBrowserLocationChange;
FOnDocumentBegin: TNotifyEvent;
FOnDocumentComplete: TNotifyEvent;
//FOnSecurityChange: TGeckoBrowserSecurityChange;
// nsIEmbeddingSiteWindow
FOnTitleChange: TGeckoBrowserTitleChange;
FOnVisibleChange: TGeckoBrowserVisibleChange;
// nsIContextMenuListener
FOnContextMenu: TGeckoBrowserContextMenu;
// nsISHistoryListener
FOnGoBack: TGeckoBrowserHistoryMove;
FOnGoForward: TGeckoBrowserHistoryMove;
FOnGoToIndex: TGeckoBrowserHistoryGoTo;
FOnNewWindow: TGeckoBrowserNewWindow;
FOnSetupProperties: TNotifyEvent;
FOnDirectoryService: TGeckoBrowserDirectoryService;
FGeckoComponentsStartupSucceeded: boolean;
//Linked event components
FPromptService: TGeckoPrompt;
//misc settings
FDisableJavaScript: Boolean;
FInitializationStarted: Boolean;
FInitialized: Boolean;
//Designtime graphic
FDesignTimeLogo: TPortableNetworkGraphic;
function GetDisableJavaScript: Boolean;
procedure SetDisableJavascript(const AValue: Boolean);
procedure ShutdownWebBrowser;
procedure InnerLoadURI(uri: WideString; Flags: PRUint32;
referer: nsIURI; postData, headers: TStream);
procedure SetChrome(aChrome: TCustomGeckoBrowserChrome);
procedure SetListener(aListener: TCustomGeckoBrowserListener);
procedure WMGetDlgCode(var Msg: TWMGetDlgCode); message WM_GETDLGCODE;
procedure WMEraseBkGnd(var Msg: TMessage); message WM_ERASEBKGND;
function GetContentDocument: nsIDOMDocument;
function GetContentWindow: nsIDOMWindow;
function GetCanGoBack: Boolean;
function GetCanGoForward: Boolean;
function GetWebBrowserChrome: nsIWebBrowserChrome;
function GetWebBrowserFind: nsIWebBrowserFind;
function GetWebBrowserPrint: nsIWebBrowserPrint;
function GetWebNavigation: nsIWebNavigation;
function GetNativeWindow : nativeWindow;
//function GetMarkupDocumentViewer: nsIMarkupDocumentViewer;
//function GetDocShell: nsIDocShell;
//function GetDocumentCharsetInfo: nsIDocumentCharsetInfo;
procedure DoInitializationIfNeeded;
protected
procedure Paint; override;
public
constructor Create(AOwner: TComponent); override;
destructor Destroy; override;
procedure InitWebBrowser; //FPC port: moved from private to public
procedure LoadURI(const uri: WideString); overload;
procedure LoadURI(const uri: WideString; const referer: UTF8String);
overload;
procedure LoadURI(const uri: WideString; const referer: WideString);
overload;
procedure LoadURI(const uri: WideString; referer: nsIURI); overload;
procedure LoadURIWithFlags(const uri: WideString; Flags: PRUint32);
overload;
procedure LoadURIWithFlags(const uri: WideString; Flags: PRUint32;
const referer: UTF8String); overload;
procedure LoadURIWithFlags(const uri: WideString; Flags: PRUint32;
const referer: WideString); overload;
procedure LoadURIWithFlags(Const uri: WideString; Flags: PRUint32;
referer: nsIURI); overload;
procedure GoBack;
procedure GoForward;
procedure Reload;
procedure ReloadWithFlags(AFlags: PRUint32);
protected
function DoCreateChromeWindow(chromeFlags: Longword): nsIWebBrowserChrome; virtual; abstract;
procedure DoGeckoComponentsStartup;
// TControl
procedure Resize; override;
procedure Loaded; override;
//TWinControl
procedure CreateWnd; override;
procedure DestroyWnd; override;
protected
property Chrome: TCustomGeckoBrowserChrome
read FChrome write SetChrome;
property Listener: TCustomGeckoBrowserListener
read FListeners write SetListener;
property WebBrowser: nsIWebBrowser //begin plus7
read FWebBrowser;
property WebBrowserFind: nsIWebBrowserFind
read GetWebBrowserFind;
property WebBrowserPrint: nsIWebBrowserPrint
read GetWebBrowserPrint;
property WebNavigation: nsIWebNavigation
read GetWebNavigation;
//property MarkupDocumentViewer: nsIMarkupDocumentViewer
// read GetMarkupDocumentViewer;
//property DocShell: nsIDocShell
// read GetDocShell;
//property DocumentCharsetInfo: nsIDocumentCharsetInfo
// read GetDocumentCharsetInfo; //end plus7
property ContentWindow: nsIDOMWindow
read GetContentWindow;
property ContentDocument: nsIDOMDocument
read GetContentDocument;
property CanGoBack: Boolean
read GetCanGoBack;
property CanGoForward: Boolean
read GetCanGoForward;
// �C�x���g
// nsIWebBrowserChrome
property OnStatusChange: TGeckoBrowserStatusChange
read FOnStatusChange write FOnStatusChange;
property OnProgressChange: TGeckoBrowserProgressChange
read FOnProgressChange write FOnProgressChange;
property OnLocationChange: TGeckoBrowserLocationChange
read FOnLocationChange write FOnLocationChange;
property OnDocumentBegin: TNotifyEvent
read FOnDocumentBegin write FOnDocumentBegin;
property OnDocumentComplete: TNotifyEvent
read FOnDocumentComplete write FOnDocumentComplete;
// nsIEmbeddingSiteWindow
property OnTitleChange: TGeckoBrowserTitleChange
read FOnTitleChange write FOnTitleChange;
property OnVisibleChange: TGeckoBrowserVisibleChange
read FOnVisibleChange write FOnVisibleChange;
// nsIContextMenuListener
property OnContextMenu: TGeckoBrowserContextMenu
read FOnContextMenu write FOnContextMenu;
// nsISHistoryListener
property OnGoBack:TGeckoBrowserHistoryMove
read FOnGoBack write FOnGoBack;
property OnGoForward:TGeckoBrowserHistoryMove
read FOnGoForward write FOnGoForward;
property OnGoToIndex:TGeckoBrowserHistoryGoTo
read FOnGoToIndex write FOnGoToIndex;
property OnNewWindow: TGeckoBrowserNewWindow
read FOnNewWindow write FOnNewWindow;
property OnSetupProperties: TNotifyEvent
read FOnSetupProperties write FOnSetupProperties;
property OnDirectoryService: TGeckoBrowserDirectoryService
read FOnDirectoryService write FOnDirectoryService;
// misc base settings
property DisableJavaScript: Boolean
read GetDisableJavaScript write SetDisableJavascript;
property Initialized: Boolean read FInitialized;
// Linked components set
property Prompt: TGeckoPrompt
read FPromptService write FPromptService;
end;
TCustomGeckoBrowserChrome = class(TInterfacedObject,
nsIWebBrowserChrome,
nsIWebBrowserChromeFocus,
nsIEmbeddingSiteWindow,
IGeckoBrowserChrome)
public
//constructor Create;
//destructor Destroy;
protected
// nsIWebBrowser
procedure SetStatus(statusType: PRUint32; const status: PWideChar); virtual; safecall; abstract;
function GetWebBrowser(): nsIWebBrowser; virtual; safecall; abstract;
procedure SetWebBrowser(aWebBrowser: nsIWebBrowser); virtual; safecall; abstract;
function GetChromeFlags(): PRUint32; virtual; safecall; abstract;
procedure SetChromeFlags(aChromeFlags: PRUint32); virtual; safecall; abstract;
procedure DestroyBrowserWindow(); virtual; safecall; abstract;
procedure SizeBrowserTo(aCX: PRInt32; aCY: PRInt32); virtual; safecall; abstract;
procedure ShowAsModal(); virtual; safecall; abstract;
function IsWindowModal(): PRBool; virtual; safecall; abstract;
procedure ExitModalEventLoop(aStatus: nsresult); virtual; safecall; abstract;
// nsIWebBrowserChromeFocus
procedure FocusNextElement(); virtual; safecall; abstract;
procedure FocusPrevElement(); virtual; safecall; abstract;
// nsIEmbeddingSiteWindow
procedure SetDimensions(flags: PRUint32; x: PRInt32; y: PRInt32; cx: PRInt32; cy: PRInt32); virtual; safecall; abstract;
procedure GetDimensions(flags: PRUint32; out x: PRInt32; out y: PRInt32; out cx: PRInt32; out cy: PRInt32); virtual; safecall; abstract;
procedure SetFocus(); virtual; safecall; abstract;
function GetVisibility(): PRBool; virtual; safecall; abstract;
procedure SetVisibility(aVisibility: PRBool); virtual; safecall; abstract;
function GetTitle(): PWideChar; virtual; safecall; abstract;
procedure SetTitle(const aTitle: PWideChar); virtual; safecall; abstract;
function GetSiteWindow(): Pointer; virtual; safecall; abstract;
// IGeckoBrowserChrome;
function GetCreateWindowTarget: IGeckoCreateWindowTarget; virtual; abstract;
public
function SafeCallException(obj: TObject; addr: Pointer): HRESULT; override;
end;
TCustomGeckoBrowserListener = class(TSupportsWeakReference,
nsIWebProgressListener,
nsIDOMEventListener)
private
FBrowser: TCustomGeckoBrowser;
FDOMEvents: PGeckoDOMEventRegisterArray;
public
constructor Create(ABrowser: TCustomGeckoBrowser);
//destructor Destroy;
protected
procedure InitListener(browser: TCustomGeckoBrowser); virtual;
procedure ShutdownListener(browser: TCustomGeckoBrowser); virtual;
procedure AddWebBrowserListener(browser: nsIWebBrowser); safecall;
procedure RemoveWebBrowserListener(browser: nsIWebBrowser); safecall;
// nsIWebProgressListener
procedure OnStateChange(aWebProgress: nsIWebProgress; aRequest: nsIRequest; aStateFlags: PRUint32; aStatus: nsresult); virtual; safecall; abstract;
procedure OnProgressChange(aWebProgress: nsIWebProgress; aRequest: nsIRequest; aCurSelfProgress: PRInt32; aMaxSelfProgress: PRInt32; aCurTotalProgress: PRInt32; aMaxTotalProgress: PRInt32); virtual; safecall; abstract;
procedure OnLocationChange(aWebProgress: nsIWebProgress; aRequest: nsIRequest; location: nsIURI); virtual; safecall; abstract;
procedure OnStatusChange(aWebProgress: nsIWebProgress; aRequest: nsIRequest; aStatus: nsresult; const aMessage: PWideChar); virtual; safecall; abstract;
procedure OnSecurityChange(aWebProgress: nsIWebProgress; aRequest: nsIRequest; state: PRUint32); virtual; safecall; abstract;
// nsIDOMEventListener
procedure HandleEvent(aEvent: nsIDOMEvent); safecall;
public
function SafeCallException(Obj: TObject; Addr: Pointer): HRESULT; override;
end;
{ TGeckoBrowser }
TGeckoBrowser = class(TCustomGeckoBrowser)
{$IFDEF LCLGTK2}
private
EventPool: TTimer;
procedure EventPoolProc(Sender: TObject);
{$ENDIF}
protected
FBrowser: nsIWebBrowser;
FTitle: WideString;
// Tooltip
{$IFNDEF LCL}
FHint: THintWindow;
{$ENDIF}
//DOM EventHandler
FOnDOMLoad: TGeckoBrowserDOMEventHandler;
FOnDOMClick: TGeckoBrowserDOMEventHandler;
FOnDOMMouseUp: TGeckoBrowserDOMEventHandler;
FOnDOMMouseDown: TGeckoBrowserDOMEventHandler;
FOnDOMMouseMove: TGeckoBrowserDOMEventHandler;
FOnDOMMouseScroll: TGeckoBrowserDOMEventHandler;
FOnDOMKeyUp: TGeckoBrowserDOMEventHandler;
FOnDOMKeyDown: TGeckoBrowserDOMEventHandler;
FOnDOMKeyPress: TGeckoBrowserDOMEventHandler;
FOnDOMLinkAdded: TGeckoBrowserDOMEventHandler;
FOnDOMDragOver: TGeckoBrowserDOMEventHandler;
FOnDOMDragGesture: TGeckoBrowserDOMEventHandler;
FOnDOMDragDrop: TGeckoBrowserDOMEventHandler;
FOnDOMDragExit: TGeckoBrowserDOMEventHandler;
FOnDOMFocus: TGeckoBrowserDOMEventHandler;
FOnCloseWindow: TNotifyEvent;
// The Last focused element
FLastFocused: nsIDOMElement;
function DoCreateChromeWindow(
chromeFlags: Longword): nsIWebBrowserChrome; override;
function GetURIString: UTF8String;
public
constructor Create(AOwner: TComponent); override;
destructor Destroy; override;
property Title: WideString read FTitle;
property URIString: UTF8String read GetURIString;
class function GetGeckoBrowserWithDOMWindow(constref DOMWindow: nsIDOMWindow): TGeckoBrowser;
procedure Print(const aShowPrinterSelectDialog: Boolean);
published
property OnDOMLoad: TGeckoBrowserDOMEventHandler
read FOnDOMLoad write FOnDOMLoad;
property OnDOMClick: TGeckoBrowserDOMEventHandler
read FOnDOMClick write FOnDOMClick;
property OnDOMMouseUp: TGeckoBrowserDOMEventHandler
read FOnDOMMouseUp write FOnDOMMouseUp;
property OnDOMMouseDown: TGeckoBrowserDOMEventHandler
read FOnDOMMouseDown write FOnDOMMouseDown;
property OnDOMMouseMove: TGeckoBrowserDOMEventHandler
read FOnDOMMouseMove write FOnDOMMouseMove;
property OnDOMKeyUp: TGeckoBrowserDOMEventHandler
read FOnDOMKeyUp write FOnDOMKeyUp;
property OnDOMKeyDown: TGeckoBrowserDOMEventHandler
read FOnDOMKeyDown write FOnDOMKeyDown;
property OnDOMKeyPress: TGeckoBrowserDOMEventHandler
read FOnDOMKeyPress write FOnDOMKeyPress;
property OnDOMMouseScroll: TGeckoBrowserDOMEventHandler
read FOnDOMMouseScroll write FOnDOMMouseScroll;
property OnDOMLinkAdded: TGeckoBrowserDOMEventHandler
read FOnDOMLinkAdded write FOnDOMLinkAdded;
property OnDOMDragOver: TGeckoBrowserDOMEventHandler
read FOnDOMDragOver write FOnDOMDragOver;
property OnDOMDragGesture: TGeckoBrowserDOMEventHandler
read FOnDOMDragGesture write FOnDOMDragGesture;
property OnDOMDragDrop: TGeckoBrowserDOMEventHandler
read FOnDOMDragDrop write FOnDOMDragDrop;
property OnDOMDragExit: TGeckoBrowserDOMEventHandler
read FOnDOMDragExit write FOnDOMDragExit;
property OnDOMFocus: TGeckoBrowserDOMEventHandler
read FOnDOMFocus write FOnDOMFocus;
property OnCloseWindow: TNotifyEvent
read FOnCloseWindow write FOnCloseWindow;
published
// TWinControl
property Align;
property TabOrder;
property TabStop default True;
{$IFNDEF LCL}
property BevelEdges;
property BevelInner;
property BevelKind;
property BevelOuter;
property BevelWidth;
{$ELSE}
property Anchors;
property BorderSpacing;
property Constraints;
{$ENDIF}
property BorderStyle;
property BorderWidth;
property OnLocationChange;
property OnProgressChange;
property OnStatusChange;
property OnTitleChange;
property OnVisibleChange;
property OnContextMenu;
property OnNewWindow;
property OnDocumentBegin;
property OnDocumentComplete;
property OnGoBack;
property OnGoForward;
property OnGoToIndex;
property OnSetupProperties;
property OnDirectoryService;
property DisableJavaScript;
property Prompt;
public
property ContentDocument;
property ContentWindow;
property CanGoBack;
property CanGoForward;
end;
{ TGeckoBrowserChrome }
TGeckoBrowserChrome = class(TCustomGeckoBrowserChrome,
nsIInterfaceRequestor_std19,
nsIContextMenuListener2,
nsITooltipListener)
private
FBrowser: TGeckoBrowser;
protected
public
constructor Create(Browser: TGeckoBrowser);
destructor Destroy; override;
protected
// nsIWebBrowserChrome
procedure SetStatus(statusType: PRUint32; const status: PWideChar); override;
function GetWebBrowser(): nsIWebBrowser; override;
procedure SetWebBrowser(aWebBrowser: nsIWebBrowser); override;
function GetChromeFlags(): PRUint32; override; {$IFDEF FPC} safecall; {$ENDIF}
procedure SetChromeFlags(aChromeFlags: PRUint32); override;
procedure DestroyBrowserWindow(); override;
procedure SizeBrowserTo(aCX: PRInt32; aCY: PRInt32); override;
procedure ShowAsModal(); override;
function IsWindowModal(): PRBool; override; {$IFDEF FPC} safecall; {$ENDIF}
procedure ExitModalEventLoop(aStatus: nsresult); override;
// nsIWebBrowserChromeFocus
procedure FocusNextElement(); override;
procedure FocusPrevElement(); override;
// nsIEmbeddingSiteWindow
procedure SetDimensions(flags: PRUint32; x: PRInt32; y: PRInt32; cx: PRInt32; cy: PRInt32); override;
procedure GetDimensions(flags: PRUint32; out x: PRInt32; out y: PRInt32; out cx: PRInt32; out cy: PRInt32); override;
procedure SetFocus(); override;
function GetVisibility(): PRBool; override; {$IFDEF FPC} safecall; {$ENDIF}
procedure SetVisibility(aVisibility: PRBool); override;
function GetTitle(): PWideChar; override; {$IFDEF FPC} safecall; {$ENDIF}
procedure SetTitle(const aTitle: PWideChar); override;
function GetSiteWindow(): Pointer; override; {$IFDEF FPC} safecall; {$ENDIF}
// nsIInterfaceRequestor
function NS_GetInterface(constref uuid: TGUID; out _result): nsresult; extdecl;
function nsIInterfaceRequestor_std19.GetInterface = NS_GetInterface;
// nsIContextMenuListener2
procedure OnShowContextMenu(aContextFlags: PRUint32;
aUtils: nsIContextMenuInfo); safecall;
// nsITooltipListener
procedure OnShowTooltip(aXCoords: PRInt32; aYCoords: PRInt32; const aTipText: PWideChar); safecall;
procedure OnHideTooltip(); safecall;
// IGeckoBrowserChrome;
function GetCreateWindowTarget: IGeckoCreateWindowTarget; override;
end;
TGeckoBrowserListener = class(TCustomGeckoBrowserListener,
nsIWebProgressListener,
nsISHistoryListener,
nsIDOMEventListener)
protected
// nsIWebProgressListener
procedure OnStateChange(aWebProgress: nsIWebProgress; aRequest: nsIRequest; aStateFlags: PRUint32; aStatus: nsresult); override;
procedure OnProgressChange(aWebProgress: nsIWebProgress; aRequest: nsIRequest; aCurSelfProgress: PRInt32; aMaxSelfProgress: PRInt32; aCurTotalProgress: PRInt32; aMaxTotalProgress: PRInt32); override;
procedure OnLocationChange(aWebProgress: nsIWebProgress; aRequest: nsIRequest; location: nsIURI); override;
procedure OnStatusChange(aWebProgress: nsIWebProgress; aRequest: nsIRequest; aStatus: nsresult; const aMessage: PWideChar); override;
procedure OnSecurityChange(aWebProgress: nsIWebProgress; aRequest: nsIRequest; state: PRUint32); override;
// nsISHistoryListener
procedure OnHistoryNewEntry(aNewURI: nsIURI); safecall;
function OnHistoryGoBack(aBackURI: nsIURI): PRBool; safecall;
function OnHistoryGoForward(aForwardURI: nsIURI): PRBool; safecall;
function OnHistoryReload(aReloadURI: nsIURI; aReloadFlags: PRUint32): PRBool; safecall;
function OnHistoryGotoIndex(aIndex: PRInt32; aGotoURI: nsIURI): PRBool; safecall;
function OnHistoryPurge(aNumEntries: PRInt32): PRBool; safecall;
// nsIDOMEventListener
//procedure HandleEvent(aEvent: nsIDOMEvent); safecall;
public
constructor Create(browser: TGeckoBrowser);
end;
(*TGeckoBrowser = class(TCustomControl,
nsISHistoryListener)
private
{ Private 錾 }
FWebBrowser: nsIWebBrowser;
FDocTitle: WideString;
// �C�x���g
FOnNewWindow: TGeckoBrowserNewWindow;
// nsISHistoryListener
function OnHistoryNewEntry(aNewURI: nsIURI): Longword; extdecl;
function OnHistoryGoBack(aBackURI: nsIURI; out aContinue: LongBool): Longword; extdecl;
function OnHistoryGoForward(aForwardURI: nsIURI; out aContinue: LongBool): Longword; extdecl;
function OnHistoryReload(aReloadURI: nsIURI; aReloadFlags: Longword; out aContinue: LongBool): Longword; extdecl;
function OnHistoryGotoIndex(aIndex: Longint; aGotoURI: nsIURI; out aContinue: LongBool): Longword; extdecl;
function OnHistoryPurge(aNumEntries: Longint; out aContinue: LongBool): Longword; extdecl;
function GetHistoryEntry(index: Integer): TGeckoBrowserHisoty;
function GetHistoryPosition: Integer;
function GetHistoryCount: Integer;
protected
{ Protected 錾 }
// TControl
procedure Resize; override;
public
{ Public 錾 }
// �i�r�Q[�V����
// nsIWebNavigation
procedure GotoIndex(aIndex: Integer);
property HistoryEntry[index: Integer]: TGeckoBrowserHisoty read GetHistoryEntry;
property HistoryPosition: Integer read GetHistoryPosition;
property HistoryCount: Integer read GetHistoryCount;
published
{ Published 錾 }
// TWinControl
property Align;
property TabOrder;
property TabStop default True;
property BevelEdges;
property BevelInner;
property BevelKind;
property BevelOuter;
property BevelWidth;
//property BorderWidth;
property OnCanResize;
//property OnCanMove;
property OnMouseDown;
property OnMouseMove;
property OnMouseUp;
property OnMouseWheel;
property OnMouseWheelDown;
property OnMouseWheelUp;
property OnKeyDown;
property OnKeyPress;
property OnKeyUp;
property OnStatusTextChange: TGeckoBrowserStatusChange read FOnStatusChange write FOnStatusChange;
property OnNewWindow: TGeckoBrowserNewWindow read FOnNewWindow write FOnNewWindow;
property OnProgressChange: TGeckoBrowserProgressChange read FOnProgressChange write FOnProgressChange;
property OnTitleChange: TGeckoBrowserTitleChange read FOnTitleChange write FOnTitleChange;
property OnVisible: TGeckoBrowserVisibleChange read FOnVisibleChange write FOnVisibleChange;
property OnLocationChange: TGeckoBrowserLocationChange read FOnLocationChange write FOnLocationChange;
end;*)
TCtxMenuFlags = set of (cmfLink,
cmfImage,
cmfDocument,
cmfText,
cmfInput,
cmfBGImage );
TCtxMenuInfo = class(TObject)
private
FInfo: nsIContextMenuInfo;
FFlags: TCtxMenuFlags;
// function GetMouseEvent: nsIDOMEvent;
// function GetTargetNode: nsIDOMNode;
function GetAssociatedLink: WideString;
// function GetImageContainer: imgContainer;
// function GetImageSrc: nsIURI;
function GetImageURL: UTF8String;
// function GetBGImageContainer: imgIContainer;
// function GetBGImageSrc: nsIURI;
function GetBGImageURL: UTF8String;
function GetMouseEvent: nsIDOMEvent;
function GetTargetNode: nsIDOMNode;
function GetImageContainer: imgIContainer;
function GetImageSrc: nsIURI;
function GetBGImageContainer: imgIContainer;
function GetBGImageSrc: nsIURI;
public
constructor Create(flags: Longword; info: nsIContextMenuInfo);
property Flags: TCtxMenuFlags read FFlags;
property AssociatedLink: WideString read GetAssociatedLink;
property ImageURL: UTF8String read GetImageURL;
property BGImageURL: UTF8String read GetBGImageURL;
property MouseEvent: nsIDOMEvent read GetMouseEvent;
property TargetNode: nsIDOMNode read GetTargetNode;
property ImageContainer: imgIContainer read GetImageContainer;
property ImageSrc: nsIURI read GetImageSrc;
property BGImageContainer: imgIContainer read GetBGImageContainer;
property BGImageSrc: nsIURI read GetBGImageSrc;
property ContextMenuInfo: nsIContextMenuInfo read FInfo;
end;
procedure Register;
{$IFNDEF LCL}
{$R *.dcr}
{$ELSE}
{$IFNDEF DARWIN}
{$R geckoresources.rc}
{$ENDIF}
{$ENDIF}
implementation
uses
nsError, nsStream, nsMemory, nsNetUtil, GeckoInit,
Forms, TypInfo, Variants;
var
GeckoListBrowsers: TFPList=nil;
procedure Register;
begin
RegisterComponents('Gecko', [TGeckoBrowser]);
end;
{$PUSH}
{$HINTS OFF}
procedure UseParameter(var X);
begin
end;
{$POP}
(*
// nsISHistoryListener
function TGeckoBrowser.OnHistoryNewEntry(aNewURI: nsIURI): Longword;
begin
Result := NS_OK;
end;
function TGeckoBrowser.OnHistoryGoBack(aBackURI: nsIURI; out aContinue: LongBool): Longword;
begin
if @aContinue = nil then
begin
Result := NS_ERROR_FAILURE;
Exit;
end;
if (HistoryPosition>0) then
aContinue := True
else
aContinue := False;
Result := NS_OK;
end;
function TGeckoBrowser.OnHistoryGoForward(aForwardURI: nsIURI; out aContinue: LongBool): Longword;
begin
if @aContinue = nil then
begin
Result := NS_ERROR_FAILURE;
Exit;
end;
if (HistoryPosition+1)<HistoryCount then
aContinue := True
else
aContinue := False;
Result := NS_OK;
end;
function TGeckoBrowser.OnHistoryReload(aReloadURI: nsIURI; aReloadFlags: Longword; out aContinue: LongBool): Longword;
begin
if @aContinue = nil then
begin
Result := NS_ERROR_FAILURE;
Exit;
end;
aContinue := True;
Result := NS_OK;
end;
function TGeckoBrowser.OnHistoryGotoIndex(aIndex: Longint; aGotoURI: nsIURI; out aContinue: LongBool): Longword;
begin
if @aContinue = nil then
begin
Result := NS_ERROR_FAILURE;
Exit;
end;
if aIndex in [0..HistoryCount-1] then
aContinue := True
else
aContinue := False;
Result := NS_OK;
end;
function TGeckoBrowser.OnHistoryPurge(aNumEntries: Longint; out aContinue: LongBool): Longword;
begin
if @aContinue = nil then
begin
Result := NS_ERROR_FAILURE;
Exit;
end;
aContinue := False;
Result := NS_OK;
end;
// TControl �p�
procedure TGeckoBrowser.Resize;
var
BaseWindow: nsIBaseWindow;
rc: TRect;
begin
inherited Resize;
if not Assigned(FWebBrowser) then Exit;
BaseWindow := FWebBrowser as nsIBaseWindow;
rc := ClientRect;
BaseWindow.SetPositionAndSize(rc.Left, rc.Top, rc.Right-rc.left, rc.Bottom-rc.Top, False);
end;
procedure TGeckoBrowser.GotoIndex(aIndex: Integer);
var
nav: nsIWebNavigation;
begin
if not Supports(FWebBrowser, nsIWebNavigation, nav) then Exit;
nav.GotoIndex(aIndex);
end;
function TGeckoBrowser.GetHistoryEntry(index: Integer): TGeckoBrowserHisoty;
var
rv: Cardinal;
nav: nsIWebNavigation;
history: nsISHistory;
entry: nsIHistoryEntry;
str: IInterfacedCString;
wstr: PWideChar;
uri: nsIURI;
bool: LongBool;
begin
Result.URI := '';
Result.Title := '';
Result.IsSubFrame := False;
rv := FWebBrowser.QueryInterface(nsIWebNavigation, nav);
if NS_FAILED(rv) then Exit;
rv := nav.GetSessionHistory(history);
if NS_FAILED(rv) then Exit;
rv := history.GetEntryAtIndex(index, False, entry);
if NS_FAILED(rv) then Exit;
rv := entry.GetURI(uri);
if NS_FAILED(rv) then Exit;
str := NewCString;
rv := uri.GetSpec(str.ACString);
if NS_FAILED(rv) then Exit;
rv := entry.GetTitle(wstr);
if NS_FAILED(rv) then Exit;
rv := entry.GetIsSubFrame(bool);
if NS_FAILED(rv) then Exit;
Result.URI := str.ToString;
Result.Title := WideString(wstr);
Result.IsSubFrame := bool;
nsMemory.Free(wstr);
end;
function TGeckoBrowser.GetHistoryPosition: Integer;
var
nav: nsIWebNavigation;
history: nsISHistory;
begin
Result := -1;
if NS_FAILED(FWebBrowser.QueryInterface(nsIWebNavigation, nav)) then Exit;
if NS_FAILED(nav.GetSessionHistory(history)) then Exit;
history.GetIndex(Result);
end;
function TGeckoBrowser.GetHistoryCount: Integer;
var
nav: nsIWebNavigation;
history: nsISHistory;
begin
Result := 0;
if NS_FAILED(FWebBrowser.QueryInterface(nsIWebNavigation, nav)) then Exit;
if NS_FAILED(nav.GetSessionHistory(history)) then Exit;
history.GetCount(Result);
end;
*)
function TCustomGeckoBrowserChrome.SafeCallException(obj: TObject; addr: Pointer): HRESULT;
begin
UseParameter(obj); UseParameter(Addr);
Result := E_FAIL;
end;
constructor TCustomGeckoBrowserListener.Create(ABrowser: TCustomGeckoBrowser);
begin
inherited Create;
FBrowser := ABrowser;
end;
procedure TCustomGeckoBrowserListener.InitListener(browser: TCustomGeckoBrowser);
var
I: Integer;
domWin: nsIDOMWindow;
target: nsIDOMEventTarget;
begin
AddWebBrowserListener(browser.WebBrowser);
if Assigned(FDOMEvents) then
begin
I := 0;
domWin := browser.ContentWindow;
target := (domWin as nsIDOMWindow2).WindowRoot;
while FDOMEvents[I].eventType <> etNone do
begin
with FDOMEvents[I] do
begin
target.AddEventListener(NewString(Name).AString, Self, true);
end;
Inc(I);
end;
end;
end;
procedure TCustomGeckoBrowserListener.ShutdownListener(browser: TCustomGeckoBrowser);
var
I: Integer;
domWin: nsIDOMWindow;
target: nsIDOMEventTarget;
begin
RemoveWebBrowserListener(browser.WebBrowser);
if Assigned(FDOMEvents) then
begin
I := 0;
domWin := browser.ContentWindow;
target := (domWin as nsIDOMWindow2).WindowRoot;
while FDOMEvents[I].eventType <> etNone do
begin
with FDOMEvents[I] do
begin
target.AddEventListener(NewString(Name).AString, Self, False);
end;
Inc(I);
end;
end;
end;
procedure TCustomGeckoBrowserListener.AddWebBrowserListener(browser: nsIWebBrowser);
var
weak: nsIWeakReference;
table: PInterfaceTable;
i: Integer;
begin
weak := GetWeakReference;
table := ClassType.GetInterfaceTable;
if Assigned(table) then
for i:=0 to table.EntryCount-1 do
{$IFNDEF FPC}
browser.AddWebBrowserListener(weak, table.Entries[i].IID);
{$ELSE}
{$PUSH}
{$R-}
browser.AddWebBrowserListener(weak, table.Entries[i].IID^); //FPC Entries is only array[0..0]!
{$POP}
{$ENDIF}
end;
procedure TCustomGeckoBrowserListener.RemoveWebBrowserListener(browser: nsIWebBrowser);
var
weak: nsIWeakReference;
table: PInterfaceTable;
i: Integer;
begin
weak := GetWeakReference;
table := ClassType.GetInterfaceTable;
if Assigned(table) then
for i:=0 to table.EntryCount-1 do
{$IFNDEF FPC}
browser.RemoveWebBrowserListener(weak, table.Entries[i].IID);
{$ELSE}
{$PUSH}
{$R-}
browser.RemoveWebBrowserListener(weak, table.Entries[i].IID^);
{$POP}
{$ENDIF}
end;
function TCustomGeckoBrowserListener.SafeCallException(
Obj: TObject; Addr: Pointer): HResult;
begin
UseParameter(obj); UseParameter(Addr);
Result := HRESULT(NS_ERROR_FAILURE);
end;
procedure TCustomGeckoBrowserListener.HandleEvent(aEvent: nsIDOMEvent);
var
i: Integer;
eventType: String;
str: IInterfacedString;
method: TMethod;
eventHandler: TGeckoBrowserDOMEventHandler;
domEvent: TGeckoDOMEvent;
begin
if Assigned(FDOMEvents) then
begin
str := NewString;
aEvent.GetType(str.AString);
eventType := str.ToString;
I := 0;
while FDOMEvents[I].eventType <>etNone do
begin
if FDOMEvents[I].Name = eventType then
begin
method := GetMethodProp(FBrowser, FDOMEvents[I].propertyName);
eventHandler := TGeckoBrowserDOMEventHandler(method);
if Assigned(eventHandler) then
begin
domEvent.Name := FDOMEvents[I].Name;
domEvent.EventType := FDOMEvents[I].eventType;
domEvent.event := aEvent;
eventHandler(FBrowser, domEvent);
end;
Exit;
end;
Inc(I);
end;
end;
end;
constructor TCustomGeckoBrowser.Create(AOwner: TComponent);
var
Logo: TResourceStream;
begin
inherited;
{$IFDEF DEBUG}
OutputDebugString('TGeckoBrowser.Create');
{$ENDIF}
if not (csDesigning in ComponentState) then
begin
end else begin
Logo:=TResourceStream.Create(HINSTANCE,'ID_GECKO_LOGO',pchar(RT_RCDATA));
FDesignTimeLogo:=TPortableNetworkGraphic.Create;
FDesignTimeLogo.LoadFromStream(Logo);
Logo.Free;
end;
end;
destructor TCustomGeckoBrowser.Destroy;
begin
{$IFDEF DEBUG}
OutputDebugString('TGeckoBrowser.Destroy');
{$ENDIF}
if assigned(FDesignTimeLogo) then
FreeAndNil(FDesignTimeLogo);
ShutdownWebBrowser;
Chrome := nil;
Listener := nil;
if FGeckoComponentsStartupSucceeded then
GeckoComponentsShutdown;
inherited;
end;
// override methods from TControl
procedure TCustomGeckoBrowser.Resize;
var
baseWin: nsIBaseWindow;
rc: TRect;
begin
inherited Resize;
if not Assigned(FWebBrowser) then Exit;
baseWin := FWebBrowser as nsIBaseWindow;
rc := GetClientRect;
baseWin.SetPositionAndSize(rc.Left, rc.Top, rc.Right - rc.Left, rc.Bottom - rc.Top, False);
end;
procedure TCustomGeckoBrowser.Loaded;
begin
if not (csDesigning in ComponentState) then
begin
DoGeckoComponentsStartup;
end;
inherited Loaded;
DoInitializationIfNeeded;
end;
procedure TCustomGeckoBrowser.CreateWnd;
begin
{$IFDEF DEBUG}
OutputDebugString('TGeckoBrowser.CreateWnd');
{$ENDIF}
inherited CreateWnd;
if not (csDesigning in ComponentState) and not FGeckoComponentsStartupSucceeded and not FInitializationStarted then
begin
DoGeckoComponentsStartup;
DoInitializationIfNeeded;
end;
end;
procedure TCustomGeckoBrowser.DestroyWnd;
begin
{$IFDEF DEBUG}
OutputDebugString('TGeckoBrowser.DestroyWnd');
{$ENDIF}
inherited DestroyWnd;
if not FGeckoComponentsStartupSucceeded then
FreeAndNIL(GeckoEngineDirectoryService);
end;
procedure TCustomGeckoBrowser.GoBack;
begin
try
(FWebBrowser as nsIWebNavigation).GoBack;
except
raise EGeckoBrowserNavigationError.CreateRes(
PResStringRec(@SGeckoBrowserCannotGoBack));
end;
end;
procedure TCustomGeckoBrowser.GoForward;
begin
try
(FWebBrowser as nsIWebNavigation).GoForward;
except
raise EGeckoBrowserNavigationError.CreateRes(
PResStringRec(@SGeckoBrowserCannotGoForward));
end;
end;
procedure TCustomGeckoBrowser.InitWebBrowser;
var
baseWin: nsIBaseWindow;
focus: nsIWebBrowserFocus;
rc: TRect;
begin
// Initialize WindowCreator
if not InitWindowCreator then
raise EGeckoBrowserError.CreateRes(PResStringRec(@SGeckoBrowserInitError));
// Create Browser Object
NS_CreateInstance(NS_WEBBROWSER_CID, nsIWebBrowser, FWebBrowser);
try
// Initialize Browser
FWebBrowser.ContainerWindow := FChrome;
baseWin := FWebBrowser as nsIBaseWindow;
rc := ClientRect;
baseWin.InitWindow(getNativeWindow,
nil,
rc.Left,
rc.Top,
rc.Right-rc.Left,
rc.Bottom-rc.Top);
baseWin.Create();
// Register Listeners
FListeners.InitListener(Self);
// Show Browser
baseWin.SetVisibility(True);
// Activate Focus
focus := FWebBrowser as nsIWebBrowserFocus;
focus.Activate;
except
raise EGeckoBrowserError.CreateRes(PResStringRec(@SGeckoBrowserInitError));
end;
end;
procedure TCustomGeckoBrowser.InnerLoadURI(uri: WideString;
Flags: PRUint32; referer: nsIURI; postData, headers: TStream);
var
nav: nsIWebNavigation;
post: nsIInputStream;
head: nsIInputStream;
begin
try
nav := FWebBrowser as nsIWebNavigation;
if Assigned(postData) then
post := NS_NewInputStreamFromTStream(postData, True);
if Assigned(headers) then
head := NS_NewInputStreamFromTStream(headers, True);
nav.LoadURI(PWideChar(uri), Flags, referer, post, head);
except
raise EGeckoBrowserNavigationError.CreateResFmt(
PResStringRec(@SGeckoBrowserLoadURIError),
[String(uri)]);
end;
end;
procedure TCustomGeckoBrowser.LoadURI(const uri: WideString);
begin
if FGeckoComponentsStartupSucceeded then
InnerLoadURI(uri, 0, nil, nil, nil);
end;
procedure TCustomGeckoBrowser.LoadURI(const uri: WideString;
const referer: UTF8String);
var
ref: nsIURI;
refStr: IInterfacedUTF8String;
begin
refStr := NewUTF8String(referer);
ref := NS_NewURI(refStr.AUTF8String);
InnerLoadURI(uri, 0, ref, nil, nil);
end;
procedure TCustomGeckoBrowser.LoadURI(const uri: WideString; const referer: WideString);
var
ref: nsIURI;
refStr: IInterfacedUTF8String;
begin
refStr := NewUTF8String(UTF8String(referer));
ref := NS_NewURI(refStr.AUTF8String);
InnerLoadURI(uri, 0, ref, nil, nil);
end;
procedure TCustomGeckoBrowser.LoadURI(const uri: WideString; referer: nsIURI);
begin
InnerLoadURI(uri, 0, referer, nil, nil);
end;
procedure TCustomGeckoBrowser.LoadURIWithFlags(const uri: WideString;
Flags: PRUint32);
begin
InnerLoadURI(uri, Flags, nil, nil, nil);
end;
procedure TCustomGeckoBrowser.LoadURIWithFlags(const uri: WideString;
Flags: PRUint32; const referer: UTF8String);
var
ref: nsIURI;
refStr: IInterfacedUTF8String;
begin
refStr := NewUTF8String(UTF8String(referer));
ref := NS_NewURI(refStr.AUTF8String);
InnerLoadURI(uri, Flags, ref, nil, nil);
end;
procedure TCustomGeckoBrowser.LoadURIWithFlags(const uri: WideString; Flags: PRUint32; const referer: WideString);
var
ref: nsIURI;
refStr: IInterfacedUTF8String;
begin
refStr := NewUTF8String(UTF8String(referer));
ref := NS_NewURI(refStr.AUTF8String);
InnerLoadURI(uri, Flags, ref, nil, nil);
end;
procedure TCustomGeckoBrowser.LoadURIWithFlags(const uri: WideString; Flags: PRUint32; referer: nsIURI);
begin
InnerLoadURI(uri, Flags, referer, nil, nil);
end;
procedure TCustomGeckoBrowser.Reload;
begin
ReloadWithFlags(NS_IWEBNAVIGATION_LOAD_FLAGS_NONE);
end;
procedure TCustomGeckoBrowser.ReloadWithFlags(AFlags: PRUint32);
var
nav: nsIWebNavigation;
begin
try
nav := FWebBrowser as nsIWebNavigation;
nav.Reload(AFlags);
except
raise EGeckoBrowserNavigationError.CreateRes(
PResStringRec(@SGeckoBrowserCannotReload));
end;
end;
procedure TCustomGeckoBrowser.DoGeckoComponentsStartup;
begin
if not Assigned(GeckoEngineDirectoryService) then begin
//This interface must be created as soon as possible because it
//will be callbacked when starting the XRE which happend just
//after the GeckoBrowser is created but before it is ready to be
//used. The setup of this component is a one time operation, called
//by the FIRST instance of GeckoBrowser and not called by the next
//ones; and its data persists while the program is running.
GeckoEngineDirectoryService:=IDirectoryServiceProvider.Create;
end;
if Assigned(FOnDirectoryService) then
FOnDirectoryService(Self,GeckoEngineDirectoryService);
try
GeckoComponentsStartup;
FGeckoComponentsStartupSucceeded := true;
//Create the prompt service and register
RegisterPromptService;
except
FGeckoComponentsStartupSucceeded := false;
end;
end;
procedure TCustomGeckoBrowser.ShutdownWebBrowser;
begin
if Assigned(FWebBrowser) then
begin
//FListeners.RemoveWebBrowserListener(FWebBrowser);
FListeners.ShutdownListener(Self);
FWebBrowser.SetContainerWindow(nil);
FWebBrowser := nil;
end;
end;
function TCustomGeckoBrowser.GetDisableJavaScript: Boolean;
begin
Result:=FDisableJavaScript;
end;
procedure TCustomGeckoBrowser.SetDisableJavascript(const AValue: Boolean);
var
iWebSetup: nsIWebBrowserSetup;
begin
try
if FInitialized then begin
iWebSetup:=Self.FWebBrowser as nsIWebBrowserSetup;
iWebSetup.SetProperty(NS_IWEBBROWSERSETUP_SETUP_ALLOW_JAVASCRIPT,PRInt32(not AValue));
end;
FDisableJavaScript:=AValue;
except
try
Raise EGeckoHint.Create('Unable to disable JavaScript at this moment. Gecko not created?');
except
end;
end;
end;
procedure TCustomGeckoBrowser.SetChrome(aChrome: TCustomGeckoBrowserChrome);
var
old: TCustomGeckoBrowserChrome;
begin
old := FChrome;
FChrome := aChrome;
if Assigned(FChrome) then
FChrome._AddRef;
if Assigned(old) then old._Release;
end;
procedure TCustomGeckoBrowser.SetListener(aListener: TCustomGeckoBrowserListener);
var
old: TCustomGeckoBrowserListener;
begin
old := FListeners;
FListeners := aListener;
if Assigned(FListeners) then
FListeners._AddRef;
if Assigned(old) then old._Release;
end;
procedure TCustomGeckoBrowser.WMGetDlgCode(var Msg: TWMGetDlgCode);
begin
Msg.Result := Msg.Result or DLGC_WANTARROWS or DLGC_WANTTAB;
end;
constructor TGeckoBrowserChrome.Create(Browser: TGeckoBrowser);
begin
inherited Create;
FBrowser := Browser;
end;
destructor TGeckoBrowserChrome.Destroy;
begin
inherited Destroy;
end;
procedure TGeckoBrowserChrome.SetStatus(
statusType: PRUint32;
const status: PWideChar);
begin
{$IFDEF DEBUG}
{
OutputDebugString(PChar(
'GeckoBrowser.SetStatus('+status+')'
));
}
{$ENDIF}
UseParameter(statusType);
if Assigned(FBrowser.OnStatusChange) then
FBrowser.OnStatusChange(FBrowser, status);
end;
function TGeckoBrowserChrome.GetWebBrowser()
: nsIWebBrowser;
begin
Result := FBrowser.FWebBrowser;
end;
procedure TGeckoBrowserChrome.SetWebBrowser(
aWebBrowser: nsIWebBrowser);
begin
FBrowser.FWebBrowser := aWebBrowser;
end;
function TGeckoBrowserChrome.GetChromeFlags()
: PRUint32;
begin
//TODO 2 -cTGeckoBrowserChrome: Chrome �t���O�̈������ǂ����悤��
Result := NS_IWEBBROWSERCHROME_CHROME_DEFAULT;
end;
procedure TGeckoBrowserChrome.SetChromeFlags(
aChromeFlags: PRUint32);
begin
UseParameter(aChromeFlags);
end;
procedure TGeckoBrowserChrome.DestroyBrowserWindow();
begin
if Assigned(FBrowser.FOnCloseWindow) then
FBrowser.FOnCloseWindow(FBrowser);
end;
procedure TGeckoBrowserChrome.SizeBrowserTo(
aCX: PRInt32;
aCY: PRInt32);
begin
FBrowser.Width := aCX;
FBrowser.Height:= aCY;
end;
procedure TGeckoBrowserChrome.ShowAsModal();
begin
end;
function TGeckoBrowserChrome.IsWindowModal()
: PRBool;
begin
Result := False;
end;
procedure TGeckoBrowserChrome.ExitModalEventLoop(
aStatus: nsresult);
begin
UseParameter(aStatus);
end;
procedure TGeckoBrowserChrome.SetDimensions(
flags: PRUint32;
x: PRInt32;
y: PRInt32;
cx: PRInt32;
cy: PRInt32);
const
FLAGS_POSITION = ns_IEmbeddingSiteWindow_DIM_FLAGS_POSITION;
FLAGS_SIZE_INNER = ns_IEmbeddingSiteWindow_DIM_FLAGS_SIZE_INNER;
FLAGS_SIZE_OUTER = ns_IEmbeddingSiteWindow_DIM_FLAGS_SIZE_OUTER;
var
bounds: TRect;
clientrect: TRect;
w, h: Integer;
begin
bounds := FBrowser.BoundsRect;
clientrect := FBrowser.ClientRect;
w := bounds.Right - bounds.Left;
h := bounds.Bottom - bounds.Top;
if (flags and FLAGS_POSITION)<>0 then
begin
if (flags and FLAGS_SIZE_INNER)<>0 then
begin
SetRect(bounds, x, y, x+(w-clientrect.Right)+cx, y+(h-clientrect.Bottom)+cy);
end else
if (flags and FLAGS_SIZE_OUTER)<>0 then
begin
SetRect(bounds, x, y, x+cx, y+cy);
end else
begin
SetRect(bounds, x, y, x+w, y+h);
end;
end else
if (flags and FLAGS_SIZE_INNER)<>0 then
begin
bounds.Right := bounds.Left + x+(w-clientrect.Right)+cx;
bounds.Bottom := bounds.Top + y+(h-clientrect.Bottom)+cy;
end else
if (flags and FLAGS_SIZE_OUTER)<>0 then
begin
bounds.Right := bounds.Left + cx;
bounds.Bottom := bounds.Top + cy;
end;
FBrowser.BoundsRect := bounds;
end;
procedure TGeckoBrowserChrome.GetDimensions(
flags: PRUint32;
out x: PRInt32;
out y: PRInt32;
out cx: PRInt32;
out cy: PRInt32);
const
FLAGS_POSITION = NS_IEMBEDDINGSITEWINDOW_DIM_FLAGS_POSITION;
FLAGS_SIZE_INNER = NS_IEMBEDDINGSITEWINDOW_DIM_FLAGS_SIZE_INNER;
FLAGS_SIZE_OUTER = NS_IEMBEDDINGSITEWINDOW_DIM_FLAGS_SIZE_OUTER;
begin
if (flags and FLAGS_POSITION)<>0 then
begin
x := FBrowser.Left;
y := FBrowser.Top;
end;
if (flags and FLAGS_SIZE_INNER)<>0 then
begin
cx := FBrowser.ClientWidth;
cy := FBrowser.ClientHeight;
end;
if (flags and FLAGS_SIZE_OUTER)<>0 then
begin
cx := FBrowser.Width;
cy := FBrowser.Height;
end;
end;
procedure TGeckoBrowserChrome.SetFocus();
begin
if Assigned(FBrowser.FOnVisibleChange) then begin
//Give the browser a chance to become visible
FBrowser.FOnVisibleChange(FBrowser,true);
end;
try
FBrowser.SetFocus;
except
Raise EGeckoHint.Create('Unable to set focus to '+FBrowser.Name);
end;
end;
function TGeckoBrowserChrome.GetVisibility(): PRBool;
begin
// TODO 1 -cTGeckoBrowserChrome: TGeckoBrowserChrome.GetVisibility �͂ǂ����ׂ���
Result := True;
end;
procedure TGeckoBrowserChrome.SetVisibility(
aVisibility: PRBool);
begin
UseParameter(aVisibility);
//TODO 1 -cTGeckoBrowserChrome: TGeckoBrowserChrome.SetVisibility �̎���
end;
function TGeckoBrowserChrome.GetTitle(): PWideChar;
var
pstr: PWideChar;
title: WideString;
len: Integer;
begin
title := FBrowser.FTitle;
len := Length(title);
pstr := PWideChar(title);
Result := nsMemory.Clone(pstr, (len+1)*2);
if not Assigned(Result) then
OutOfMemoryError;
end;
procedure TGeckoBrowserChrome.SetTitle(
const aTitle: PWideChar);
begin
FBrowser.FTitle := aTitle;
if Assigned(FBrowser.OnTitleChange) then
FBrowser.OnTitleChange(FBrowser, FBrowser.FTitle);
end;
function TGeckoBrowserChrome.GetSiteWindow(): Pointer;
begin
{$PUSH}
{$HINTS OFF}
Result := Pointer(FBrowser.Handle);
{$POP}
end;
constructor TGeckoBrowserListener.Create(browser: TGeckoBrowser);
const
//Most usual events at the beginning to improve handling speed.
events: array [0..15] of TGeckoDOMEventRegister = (
(name:'mousemove'; eventType:etMouseEvent; propertyName:'OnDOMMouseMove' ),
(name:'DOMMouseScroll'; eventType: etMouseEvent;propertyName:'OnDOMMouseScroll'),
(name:'focus'; eventType:etEvent; propertyName:'OnDOMFocus'),
(name:'load'; eventType:etEvent; propertyName:'OnDOMLoad' ),
(name:'click'; eventType:etMouseEvent; propertyName:'OnDOMClick' ),
(name:'mouseup'; eventType:etMouseEvent; propertyName:'OnDOMMouseUp' ),
(name:'mousedown'; eventType:etMouseEvent; propertyName:'OnDOMMouseDown' ),
(name:'keyup'; eventType:etEvent; propertyName:'OnDOMKeyUp' ),
(name:'keydown'; eventType:etEvent; propertyName:'OnDOMKeyDown'),
(name:'keypress'; eventType:etEvent; propertyName:'OnDOMKeyPress'),
(name:'DOMLinkAdded'; eventType: etEvent; propertyName:'OnDOMLinkAdded'),
(name:'dragover'; eventType:etEvent; propertyName:'OnDOMDragOver'),
(name:'draggesture'; eventType:etEvent; propertyName:'OnDOMDragGesture'),
(name:'dragdrop'; eventType:etEvent; propertyName:'OnDOMDragDrop'),
(name:'dragexit'; eventType:etEvent; propertyName:'OnDOMDragExit'),
(name:''; eventType:etNone; propertyName:'')
);
begin
inherited Create(browser);
FDOMEvents := PGeckoDOMEventRegisterArray(@events);
end;
procedure TGeckoBrowserListener.OnStateChange(
aWebProgress: nsIWebProgress;
aRequest: nsIRequest;
aStateFlags: PRUint32;
aStatus: nsresult);
{$IFDEF DEBUG}
var
uri: nsIURI;
str: IInterfacedCString;
channel: nsIChannel;
{$ENDIF}
const
STATE_IS_DOCUMENT = NS_IWEBPROGRESSLISTENER_STATE_IS_DOCUMENT;
STATE_IS_NETWORK = NS_IWEBPROGRESSLISTENER_STATE_IS_NETWORK;
STATE_START = NS_IWEBPROGRESSLISTENER_STATE_START;
STATE_STOP = NS_IWEBPROGRESSLISTENER_STATE_STOP;
begin
UseParameter(aWebProgress);
UseParameter(aRequest);
UseParameter(aStatus);
if (aStateFlags and STATE_IS_DOCUMENT)<>0 then
begin
// ��Ԃ̕ω��̓h�L������g�ɑ΂��Ăł���
if (aStateFlags and STATE_START)<>0 then
begin
// �h�L������g�̓ǂݞ�݂��J�n���ꂽ
{$IFDEF DEBUG}
{
OutputDebugString('GeckoBrowser.OnDocumentBegin');
}
{$ENDIF}
if Assigned(FBrowser.OnDocumentBegin) then
FBrowser.OnDocumentBegin(Self);
end else
if (aStateFlags and STATE_STOP)<>0 then
begin
// �h�L������g�̓ǂݞ�݂���������
{$IFDEF DEBUG}
{
OutputDebugString('GeckoBrowser.OnDocumentComplete');
}
{$ENDIF}
if Assigned(FBrowser.OnDocumentComplete) then
FBrowser.OnDocumentComplete(Self);
if Assigned(FBrowser.OnStatusChange) then
FBrowser.OnStatusChange(FBrowser, '');
end;
end;
if (aStateFlags and STATE_IS_NETWORK)<>0 then
begin
// ��Ԃ̕ω��̓l�b�g�[�N�ɑ΂��Ăł���
if (aStateFlags and STATE_START)<>0 then
begin
// �l�b�g�[�N�̓]�����J�n���ꂽ��
{$IFDEF DEBUG}
{
str := NewCString;
channel := aRequest as nsIChannel;
uri := channel.URI;
uri.GetSpec(str.ACString);
OutputDebugStringA(
PAnsiChar('GeckoBrowser.OnDownloadBegin('+str.ToString+')'));
}
{$ENDIF}
end else
if (aStateFlags and STATE_STOP)<>0 then
begin
// �l�b�g�[�N�̓]����I��������
{$IFDEF DEBUG}
{
str := NewCString;
channel := aRequest as nsIChannel;
uri := channel.URI;
uri.GetSpec(str.ACString);
OutputDebugStringA(
PAnsiChar('GeckoBrowser.OnDownloadComplete('+str.ToString+')'));
}
{$ENDIF}
if Assigned(FBrowser.OnStatusChange) then
FBrowser.OnStatusChange(FBrowser, '');
end;
end;
end;
procedure TGeckoBrowserListener.OnProgressChange(
aWebProgress: nsIWebProgress;
aRequest: nsIRequest;
aCurSelfProgress: PRInt32;
aMaxSelfProgress: PRInt32;
aCurTotalProgress: PRInt32;
aMaxTotalProgress: PRInt32);
begin
UseParameter(aWebProgress);
UseParameter(aRequest);
UseParameter(aCurSelfProgress);
UseParameter(aMaxSelfProgress);
if Assigned(FBrowser.OnProgressChange) then
begin
{$IFDEF DEBUG}
{
OutputDebugString(PChar(
'OnProgressListener('+IntToStr(aCurTotalProgress)+'/'+IntToStr(aMaxTotalProgress)+')'
));
}
{$ENDIF}
FBrowser.OnProgressChange(FBrowser, aCurTotalProgress, aMaxTotalProgress);
end;
end;
procedure TGeckoBrowserListener.OnLocationChange(
aWebProgress: nsIWebProgress;
aRequest: nsIRequest;
location: nsIURI);
var
str: IInterfacedCString;
begin
UseParameter(aWebProgress);
UseParameter(aRequest);
str := NewCString;
location.GetSpec(str.ACString);
{$IFDEF DEBUG}
{
OutputDebugStringA(PAnsiChar(
'GeckoBrowser.LocationChange('+str.ToString+')'
));
}
{$ENDIF}
if Assigned(FBrowser.OnLocationChange) then
FBrowser.OnLocationChange(FBrowser, str.ToString);
end;
procedure TGeckoBrowserListener.OnStatusChange(
aWebProgress: nsIWebProgress;
aRequest: nsIRequest;
aStatus: nsresult;
const aMessage: PWideChar);
begin
UseParameter(aWebProgress);
UseParameter(aRequest);
UseParameter(aStatus);
{$IFDEF DEBUG}
{
OutputDebugStringW(PWideChar(
'GeckoBrowser.OnStatusChange('+aMessage+')'
));
}
{$ENDIF}
if Assigned(FBrowser.OnStatusChange) then
FBrowser.OnStatusChange(FBrowser, aMessage);
end;
procedure TGeckoBrowserListener.OnSecurityChange(
aWebProgress: nsIWebProgress;
aRequest: nsIRequest;
state: PRUint32);
begin
UseParameter(aWebProgress);
UseParameter(aRequest);
UseParameter(State);
//TODO 1 -cTGeckoBrowserListner: TGeckoBrowserListener.OnSecurityChange �̋Lq
end;
constructor TGeckoBrowser.Create(AOwner: TComponent);
begin
if not Assigned(GeckoListBrowsers) then GeckoListBrowsers:=TFPList.Create;
GeckoListBrowsers.Add(Self);
inherited;
Chrome := TGeckoBrowserChrome.Create(Self);
Listener := TGeckoBrowserListener.Create(Self);
{$IFDEF LCLGTK2}
//Creates a timer that forces the event queue to be pooled. This could be a
//bug in the LCL or a problem with events coming for the XULRUNNER.
//A timer of 100 ms creates the feel that everything is pooled as it comes and
//it only have a visual impact.
EventPool := TTimer.Create(Self);
EventPool.Interval:=100;
EventPool.Enabled:=true;
EventPool.OnTimer:=EventPoolProc;
{$ENDIF}
end;
destructor TGeckoBrowser.Destroy;
begin
inherited Destroy;
GeckoListBrowsers.Remove(Self);
if GeckoListBrowsers.Count=0 then FreeAndNil(GeckoListBrowsers);
end;
class function TGeckoBrowser.GetGeckoBrowserWithDOMWindow(
constref DOMWindow: nsIDOMWindow): TGeckoBrowser;
var
ThisGecko: TGeckoBrowser;
t1,t2: nsIDOMWindow;
j: integer;
begin
Result:=nil;
if Assigned(GeckoListBrowsers) then begin
for j := 0 to GeckoListBrowsers.Count-1 do begin
ThisGecko:=TGeckoBrowser(GeckoListBrowsers[j]);
t1:=ThisGecko.GetContentWindow.Parent;
t2:=DOMWindow.Parent;
if t1=t2 then begin
Result:=ThisGecko;
break;
end;
end;
end;
end;
procedure TGeckoBrowser.Print(const aShowPrinterSelectDialog: Boolean);
var
PrintInterface: nsIWebBrowserPrint;
PrintSettings: nsIPrintSettings;
begin
PrintInterface:=GetWebBrowserPrint;
if Assigned(PrintInterface) then begin
PrintSettings:=PrintInterface.GetGlobalPrintSettings;
if Assigned(PrintSettings) then begin
PrintSettings.ShowPrintProgress:=false; //true implies need of nsIWebProgressListener
PrintSettings.PrintBGImages:=true;
PrintSettings.SetPrintSilent(not aShowPrinterSelectDialog);
end;
PrintInterface.Print(PrintSettings,nil);
end;
end;
function TGeckoBrowserChrome.NS_GetInterface(constref uuid: TGUID; out _result): nsresult;
begin
if IsEqualGUID(uuid, nsIDOMWindow) then
begin
Result:= nsresult(FBrowser.GetContentWindow.QueryInterface(uuid, _result));
end else
begin
// FPC port: Result is PRUInt32, but QueryInterface returns Longint,
// so cast to nsresult to prevent range check error.
// Result := QueryInterface(uuid, _result);
Result := nsresult(QueryInterface(uuid, _result));
end;
end;
procedure TGeckoBrowserChrome.OnShowContextMenu(aContextFlags: PRUint32;
aUtils: nsIContextMenuInfo);
(*
const
CONTEXT_NONE = NS_ICONTEXTMENULISTENER2_CONTEXT_NONE;
CONTEXT_LINK = NS_ICONTEXTMENULISTENER2_CONTEXT_LINK;
CONTEXT_IMAGE = NS_ICONTEXTMENULISTENER2_CONTEXT_IMAGE;
CONTEXT_DOCUMENT = NS_ICONTEXTMENULISTENER2_CONTEXT_DOCUMENT;
CONTEXT_TEXT = NS_ICONTEXTMENULISTENER2_CONTEXT_TEXT;
CONTEXT_INPUT = NS_ICONTEXTMENULISTENER2_CONTEXT_INPUT;
CONTEXT_BACKGROUND_IMAGE = NS_ICONTEXTMENULISTENER2_CONTEXT_BACKGROUND_IMAGE;*)
var
cmenu: TCtxMenuInfo;
begin
if Assigned(FBrowser.OnContextMenu) then
begin
cmenu := TCtxMenuInfo.Create(aContextFlags, aUtils);
try
FBrowser.OnContextMenu(FBrowser, cmenu);
finally
cmenu.Free;
end;
end;
end;
procedure TGeckoBrowserChrome.OnShowTooltip(aXCoords: PRInt32; aYCoords: PRInt32; const aTipText: PWideChar); safecall;
{$IFNDEF FPC}
var
r:TRect;
p,ap:TPoint;
// height:Integer;
{$ENDIF}
begin
{$IFNDEF LCL}
if FBrowser.FHint = nil then
FBrowser.FHint := THintWindow.Create(FBrowser);
r := FBrowser.FHint.CalcHintRect(400,aTipText,nil);
// height := r.Bottom;
ap.X := aXCoords;
ap.Y := aYCoords;
p := FBrowser.ClientToScreen(ap);
r.Left:=p.x;
r.Top:=p.y-r.Bottom;
r.Right:=r.Right +p.x;
r.Bottom:=p.y;
FBrowser.FHint.ActivateHint(r,aTipText);
{$ELSE}
UseParameter(aXCoords);
UseParameter(aYCoords);
FBrowser.Hint:=aTiptext;
FBrowser.ShowHint:=true;
{$ENDIF}
end;
procedure TGeckoBrowserChrome.OnHideTooltip(); safecall;
begin
{$IFNDEF LCL}
FBrowser.FHint.ReleaseHandle;
{$ENDIF}
end;
{$IFDEF LCLGTK2}
procedure TGeckoBrowser.EventPoolProc(Sender: TObject);
begin
//Do nothing. Just a hack.
end;
{$ENDIF}
function TGeckoBrowser.DoCreateChromeWindow(
chromeFlags: Longword): nsIWebBrowserChrome;
var
newWin: TCustomGeckoBrowser;
begin
if Assigned(OnNewWindow) then
begin
newWin := nil;
OnNewWindow(Self, chromeFlags, newWin);
if Assigned(newWin) then
Result := newWin.FChrome;
end;
end;
function TCustomGeckoBrowser.GetWebBrowserChrome: nsIWebBrowserChrome;
begin
Result := FChrome;
end;
function TCustomGeckoBrowser.GetContentDocument: nsIDOMDocument;
begin
Result := FWebBrowser.ContentDOMWindow.Document;
end;
function TCustomGeckoBrowser.GetContentWindow: nsIDOMWindow;
begin
Result := FWebBrowser.ContentDOMWindow;
end;
procedure TCustomGeckoBrowser.WMEraseBkGnd(var Msg: TMessage);
begin
// Cancel erase background actions.
Msg.Result := 0;
end;
procedure TCustomGeckoBrowser.Paint;
var
rc: TRect;
baseWin: nsIBaseWindow;
begin
if csDesigning in ComponentState then
begin
rc := ClientRect;
Canvas.Brush.Color:=clWhite;
Canvas.FillRect(rc);
if Assigned(FDesignTimeLogo) then
Canvas.StretchDraw(rc,FDesignTimeLogo)
end else
begin
if FGeckoComponentsStartupSucceeded then
begin
baseWin := FWebBrowser as nsIBaseWindow;
baseWin.Repaint(true);
{$IFDEF LCLGTK2}
Self.AdjustSize;
{$ENDIF}
end
else
begin
rc := ClientRect;
Canvas.FillRect(rc);
Canvas.TextOut(0,0,SGeckoBrowserInitError);
end;
end;
inherited;
end;
function TCustomGeckoBrowser.GetCanGoBack: Boolean;
var
nav: nsIWebNavigation;
history: nsISHistory;
index: PRInt32;
begin
nav := FWebBrowser as nsIWebNavigation;
history := nav.SessionHistory;
index := history.Index;
Result := (index > 0);
end;
function TCustomGeckoBrowser.GetCanGoForward: Boolean;
var
nav: nsIWebNavigation;
history: nsISHistory;
count, index: PRInt32;
begin
nav := FWebBrowser as nsIWebNavigation;
history := nav.SessionHistory;
count := history.Count;
index := history.Index;
Result := (index+1<count);
end;
function TCustomGeckoBrowser.GetWebBrowserFind: nsIWebBrowserFind;
begin
Result := FWebBrowser as nsIWebBrowserFind;
end;
function TCustomGeckoBrowser.GetWebBrowserPrint: nsIWebBrowserPrint;
var
ir:nsIInterfaceRequestor;
wbp:nsIWebBrowserPrint;
begin
ContentWindow.QueryInterface(nsIInterfaceRequestor,ir);
ir.GetInterface(nsIWebBrowserPrint, wbp);
Result := wbp;
end;
function TCustomGeckoBrowser.GetWebNavigation: nsIWebNavigation;
begin
Result := FWebBrowser as nsIWebNavigation;
end;
function TCustomGeckoBrowser.GetNativeWindow: nativeWindow;
{$IFDEF LCLCocoa}
var
ARect : NSRect;
AView : NSView;
{$ENDIF}
begin
{$IFDEF MSWINDOWS}
Result := Handle;
{$ENDIF}
{$IFDEF LCLCarbon}
Result := nativeWindow(TCarbonWindow(Handle).Window);
{$ENDIF}
{$IFDEF LCLCocoa}
ARect := NSView(TCocoaWindow(Handle).contentView).visibleRect;
ARect.size.width := ARect.size.width - 30;
ARect.size.height := ARect.size. height - 30;
ARect.origin.x := 15;
ARect.origin.y := 15;
AView := NSView.alloc.initWithFrame(ARect);
NSView(TCocoaWindow(Handle).contentView).addSubView(AView);
//Maybe Result := nativeWindow(AView) ? for 64 bits ?
Result := THANDLE(AView);
{$ENDIF}
{$IFDEF LCLGtk}
Result := Handle;
{$ENDIF}
{$IFDEF LCLGtk2}
Result := nativeWindow(PGtkWindow(Handle)^.default_widget);
{$ENDIF}
end;
procedure TCustomGeckoBrowser.DoInitializationIfNeeded;
begin
if not FInitializationStarted and FGeckoComponentsStartupSucceeded then
if not (csDesigning in ComponentState) then
begin
FInitializationStarted:=true;
InitWebBrowser;
LoadURI('about:blank');
FInitialized:=true;
if Assigned(FOnSetupProperties) then begin
FOnSetupProperties(Self);
end;
//Set again the published properties
SetDisableJavascript(FDisableJavaScript);
end;
end;
{
function TCustomGeckoBrowser.GetMarkupDocumentViewer: nsIMarkupDocumentViewer;
var
mdv:nsIMarkupDocumentViewer;
begin
Result:=nil;
(DocShell as nsIInterfaceRequestor).GetInterface(
ns_IMarkupDocumentViewer_iid, mdv
);
Result:=mdv;
end;
function TCustomGeckoBrowser.GetDocShell: nsIDocShell;
var
ds: nsIDocShell;
begin
Result := nil;
NS_GetInterface(FWebBrowser, NS_IDOCSHELL_IID, ds);
Result := ds;
end;
function TCustomGeckoBrowser.GetDocumentCharsetInfo: nsIDocumentCharsetInfo;
begin
Result := DocShell.GetDocumentCharsetInfo;
end;
}
function TGeckoBrowser.GetURIString: UTF8String;
var
str: IInterfacedUTF8String;
begin
Result:='';
str :=NewUTF8String;
//URI
if Self.WebNavigation <> nil then
Self.WebNavigation.CurrentURI.GetSpec(str.AUTF8String);
Result := str.ToString;
end;
procedure TGeckoBrowserChrome.FocusPrevElement();
var
Ancestor: TWinControl;
begin
Ancestor := FBrowser.Parent;
while Assigned(Ancestor) and (not(Ancestor is TForm)) do
Ancestor := Ancestor.Parent;
if Assigned(Ancestor) then
PostMessage(Ancestor.Handle, WM_NEXTDLGCTL, 1, 0);
end;
procedure TGeckoBrowserChrome.FocusNextElement();
var
Ancestor: TWinControl;
begin
Ancestor := FBrowser.Parent;
while Assigned(Ancestor) and (not(Ancestor is TForm)) do
Ancestor := Ancestor.Parent;
if Ancestor <> nil then
PostMessage(Ancestor.Handle, WM_NEXTDLGCTL, 0, 0);
end;
function TGeckoBrowserChrome.GetCreateWindowTarget: IGeckoCreateWindowTarget;
begin
Supports(FBrowser, IGeckoCreateWindowTarget, Result);
end;
procedure TGeckoBrowserListener.OnHistoryNewEntry(aNewURI: nsIURI);
begin
UseParameter(aNewURI);
end;
function TGeckoBrowserListener.OnHistoryGoBack(aBackURI: nsIURI): PRBool;
var
Handled:Boolean;
aContinue:PRBool;
begin
Handled:=false;
if Assigned(FBrowser.FOnGoBack) then
FBrowser.FOnGoBack(Self,aBackURI,aContinue,Handled);
if Handled then begin
Result := aContinue;
end
else {if not Handled then }begin
{if (HistoryPosition>0) then
Result := True
else
Result := False;}
Result := True;
end;
end;
function TGeckoBrowserListener.OnHistoryGoForward(aForwardURI: nsIURI): PRBool;
var
Handled:Boolean;
aContinue:PRBool;
begin
Handled:=false;
if Assigned(FBrowser.FOnGoForward) then
FBrowser.FOnGoForward(Self,aForwardURI,aContinue,Handled);
if Handled then begin
Result := aContinue;
end
else {if not Handled then} begin
{if (HistoryPosition+1)<HistoryCount then
Result := True
else
Result := False;}
Result := True;
end;
end;
function TGeckoBrowserListener.OnHistoryReload(aReloadURI: nsIURI; aReloadFlags: PRUint32): PRBool;
begin
UseParameter(aReloadURI);
UseParameter(aReloadFlags);
Result := True;
end;
function TGeckoBrowserListener.OnHistoryGotoIndex(aIndex: PRInt32; aGotoURI: nsIURI): PRBool;
var
Handled:Boolean;
aContinue:PRBool;
begin
Handled:=false;
if Assigned(FBrowser.FOnGoToIndex) then
FBrowser.FOnGoToIndex(Self,aIndex,aGotoURI,aContinue,Handled);
if Handled then begin
Result := aContinue;
end
else begin
{if aIndex in [0..HistoryCount-1] then
Result := True
else
Result := False;}
Result := True;
end;
end;
function TGeckoBrowserListener.OnHistoryPurge(aNumEntries: PRInt32): PRBool;
begin
UseParameter(aNumEntries);
Result := True;
end;
constructor TCtxMenuInfo.Create(flags: Longword; info: nsIContextMenuInfo);
begin
inherited Create;
FInfo := info;
FFlags := [];
if 0<>(flags and ns_IContextMenuListener2_CONTEXT_LINK) then
FFlags := FFlags + [cmfLink];
if 0<>(flags and ns_IContextMenuListener2_CONTEXT_IMAGE) then
FFlags := FFlags + [cmfImage];
if 0<>(flags and ns_IContextMenuListener2_CONTEXT_DOCUMENT) then
FFlags := FFlags + [cmfDocument];
if 0<>(flags and ns_IContextMenuListener2_CONTEXT_TEXT) then
FFlags := FFlags + [cmfText];
if 0<>(flags and ns_IContextMenuListener2_CONTEXT_INPUT) then
FFlags := FFlags + [cmfInput];
if 0<>(flags and ns_IContextMenuListener2_CONTEXT_BACKGROUND_IMAGE) then
FFlags := FFlags + [cmfBGImage];
end;
function TCtxMenuInfo.GetAssociatedLink: WideString;
var
str: IInterfacedString;
begin
try
str := NewString;
FInfo.GetAssociatedLink(str.AString);
Result := str.ToString;
except
end;
end;
function TCtxMenuInfo.GetImageURL: UTF8String;
var
str: IInterfacedUTF8String;
uri: nsIURI;
begin
try
str := NewUTF8String;
uri := FInfo.GetImageSrc();
uri.GetSpec(str.AUTF8String);
Result := str.ToString;
except
end;
end;
function TCtxMenuInfo.GetBGImageURL: UTF8String;
var
str: IInterfacedUTF8String;
uri: nsIURI;
begin
try
str := NewUTF8String;
uri := FInfo.GetBackgroundImageSrc();
uri.GetSpec(str.AUTF8String);
Result := str.ToString;
except
end;
end;
function TCtxMenuInfo.GetMouseEvent: nsIDOMEvent;
begin
Result := FInfo.MouseEvent;
end;
function TCtxMenuInfo.GetTargetNode: nsIDOMNode;
begin
Result := FInfo.TargetNode;
end;
function TCtxMenuInfo.GetImageContainer: imgIContainer;
begin
Result := FInfo.ImageContainer;
end;
function TCtxMenuInfo.GetImageSrc: nsIURI;
begin
Result := FInfo.ImageSrc;
end;
function TCtxMenuInfo.GetBGImageContainer: imgIContainer;
begin
Result := FInfo.BackgroundImageContainer;
end;
function TCtxMenuInfo.GetBGImageSrc: nsIURI;
begin
Result := FInfo.BackgroundImageSrc;
end;
{$IFDEF LCL}
initialization
{$I GeckoBrowser.lrs}
{$ENDIF}
end.