Subversion Repositories fastphp

Rev

Rev 91 | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 91 Rev 107
1
unit BrowserMain;
1
unit BrowserMain;
2
 
2
 
3
{$Include 'FastPHP.inc'}
3
{$Include 'FastPHP.inc'}
4
 
4
 
5
interface
5
interface
6
 
6
 
7
uses
7
uses
8
  // TODO: "{$IFDEF USE_SHDOCVW_TLB}_TLB{$ENDIF}" does not work with Delphi 10.2
8
  // TODO: "{$IFDEF USE_SHDOCVW_TLB}_TLB{$ENDIF}" does not work with Delphi 10.2
9
  //       so you have to change the reference SHDocVw / SHDocVw_TLB yourself
9
  //       so you have to change the reference SHDocVw / SHDocVw_TLB yourself
10
  Windows, Messages, SysUtils, Variants, Classes, Graphics,
10
  Windows, Messages, SysUtils, Variants, Classes, Graphics,
11
  Controls, Forms, Dialogs, OleCtrls, SHDocVw, ExtCtrls, StrUtils,
11
  Controls, Forms, Dialogs, OleCtrls, SHDocVw, ExtCtrls, StrUtils,
12
  StdCtrls, activex, UrlMon;
12
  StdCtrls, activex, UrlMon, WebBrowserUtils;
13
 
13
 
14
type
14
type
15
  TForm2 = class(TForm)
15
  TForm2 = class(TForm)
16
    WebBrowser1: TWebBrowser;
16
    WebBrowser1: TWebBrowser;
17
    Timer1: TTimer;
17
    Timer1: TTimer;
18
    OpenDialog3: TOpenDialog;
18
    OpenDialog3: TOpenDialog;
19
    procedure Timer1Timer(Sender: TObject);
19
    procedure Timer1Timer(Sender: TObject);
20
    procedure WebBrowser1BeforeNavigate2(ASender: TObject;
20
    procedure WebBrowser1BeforeNavigate2(ASender: TObject;
21
      const pDisp: IDispatch; const URL, Flags, TargetFrameName, PostData,
21
      const pDisp: IDispatch; const URL, Flags, TargetFrameName, PostData,
22
      Headers: OleVariant; var Cancel: WordBool);
22
      Headers: OleVariant; var Cancel: WordBool);
23
    procedure WebBrowser1WindowClosing(ASender: TObject;
23
    procedure WebBrowser1WindowClosing(ASender: TObject;
24
      IsChildWindow: WordBool; var Cancel: WordBool);
24
      IsChildWindow: WordBool; var Cancel: WordBool);
25
  strict private
25
  strict private
26
    function EmbeddedWBQueryService(const rsid, iid: TGUID; out Obj{: IInterface}): HRESULT;
26
    function EmbeddedWBQueryService(const rsid, iid: TGUID; out Obj{: IInterface}): HRESULT;
27
  end;
27
  end;
28
 
28
 
29
var
29
var
30
  Form2: TForm2;
30
  Form2: TForm2;
31
 
31
 
32
implementation
32
implementation
33
 
33
 
34
{$R *.dfm}
34
{$R *.dfm}
35
 
35
 
36
uses
36
uses
37
  WebBrowserUtils, FastPHPUtils, Functions, ShellAPI;
37
  FastPHPUtils, Functions, ShellAPI;
38
 
38
 
39
// TODO: Add a lot of nice stuff to let the PHP script communicate with this host application
39
// TODO: Add a lot of nice stuff to let the PHP script communicate with this host application
40
//       For example, allow window resizing etc.  (See Microsoft HTA for inspiration)
40
//       For example, allow window resizing etc.  (See Microsoft HTA for inspiration)
41
// TODO: Ajax gives Access Denied error... Create own security manager?
41
// TODO: Ajax gives Access Denied error... Create own security manager?
42
// TODO: History doesn't work?
42
// TODO: History doesn't work?
43
// (All these ToDos: Also fix in the Editor)
43
// (All these ToDos: Also fix in the Editor)
44
// TODO: kann man eventuell auch php dateien aus einer DLL rausziehen? das wäre TOLL!!!!
44
// TODO: kann man eventuell auch php dateien aus einer DLL rausziehen? das wäre TOLL!!!!
45
// TODO: headers... cookies...
45
// TODO: headers... cookies...
46
// TODO: WebBrowser1BeforeNavigate2 mit einem DLL-callback, sodass entwickler ihre eigenen fastphp:// links machen können, z.B. um DLL-Funktionen aufzurufen! (auch in JavaScript ansteuerbar?)
46
// TODO: WebBrowser1BeforeNavigate2 mit einem DLL-callback, sodass entwickler ihre eigenen fastphp:// links machen können, z.B. um DLL-Funktionen aufzurufen! (auch in JavaScript ansteuerbar?)
47
// TODO: let the website decide if the window is maximized etc, as well as it's caption, size and icon
47
// TODO: let the website decide if the window is maximized etc, as well as it's caption, size and icon
48
// TODO: Pass parameters (argv) to PHP
48
// TODO: Pass parameters (argv) to PHP
49
 
49
 
50
type
50
type
51
  TEmbeddedSecurityManager = class(TInterfacedObject, IInternetSecurityManager)
51
  TEmbeddedSecurityManager = class(TInterfacedObject, IInternetSecurityManager)
52
  public
52
  public
53
    function GetSecuritySite(out ppSite: IInternetSecurityMgrSite): HResult; stdcall;
53
    function GetSecuritySite(out ppSite: IInternetSecurityMgrSite): HResult; stdcall;
54
    function MapUrlToZone(pwszUrl: LPCWSTR; out dwZone: DWORD; dwFlags: DWORD): HResult; stdcall;
54
    function MapUrlToZone(pwszUrl: LPCWSTR; out dwZone: DWORD; dwFlags: DWORD): HResult; stdcall;
55
    function GetSecurityId(pwszUrl: LPCWSTR; pbSecurityId: Pointer; var cbSecurityId: DWORD; dwReserved: DWORD): HResult; stdcall;
55
    function GetSecurityId(pwszUrl: LPCWSTR; pbSecurityId: Pointer; var cbSecurityId: DWORD; dwReserved: DWORD): HResult; stdcall;
56
    function ProcessUrlAction(pwszUrl: LPCWSTR; dwAction: DWORD; pPolicy: Pointer; cbPolicy: DWORD; pContext: Pointer; cbContext: DWORD; dwFlags, dwReserved: DWORD): HResult; stdcall;
56
    function ProcessUrlAction(pwszUrl: LPCWSTR; dwAction: DWORD; pPolicy: Pointer; cbPolicy: DWORD; pContext: Pointer; cbContext: DWORD; dwFlags, dwReserved: DWORD): HResult; stdcall;
57
    function QueryCustomPolicy(pwszUrl: LPCWSTR; const guidKey: TGUID; out pPolicy: Pointer; out cbPolicy: DWORD; pContext: Pointer; cbContext: DWORD; dwReserved: DWORD): HResult; stdcall;
57
    function QueryCustomPolicy(pwszUrl: LPCWSTR; const guidKey: TGUID; out pPolicy: Pointer; out cbPolicy: DWORD; pContext: Pointer; cbContext: DWORD; dwReserved: DWORD): HResult; stdcall;
58
    function SetZoneMapping(dwZone: DWORD; lpszPattern: PWideChar; dwFlags: DWORD): HResult; stdcall;
58
    function SetZoneMapping(dwZone: DWORD; lpszPattern: PWideChar; dwFlags: DWORD): HResult; stdcall;
59
    function GetZoneMappings(dwZone: DWORD;out ppenumString: IEnumString; dwFlags: DWORD): HResult; stdcall;
59
    function GetZoneMappings(dwZone: DWORD;out ppenumString: IEnumString; dwFlags: DWORD): HResult; stdcall;
60
    function SetSecuritySite(pSite: IInternetSecurityMgrSite): HResult; stdcall;
60
    function SetSecuritySite(pSite: IInternetSecurityMgrSite): HResult; stdcall;
61
  end;
61
  end;
62
 
62
 
63
function TEmbeddedSecurityManager.SetSecuritySite(pSite: IInternetSecurityMgrSite): HResult; stdcall;
63
function TEmbeddedSecurityManager.SetSecuritySite(pSite: IInternetSecurityMgrSite): HResult; stdcall;
64
begin
64
begin
65
  Result := INET_E_DEFAULT_ACTION;
65
  Result := INET_E_DEFAULT_ACTION;
66
end;
66
end;
67
function TEmbeddedSecurityManager.GetSecuritySite(
67
function TEmbeddedSecurityManager.GetSecuritySite(
68
  out ppSite: IInternetSecurityMgrSite): HResult; stdcall;
68
  out ppSite: IInternetSecurityMgrSite): HResult; stdcall;
69
begin
69
begin
70
  Result := INET_E_DEFAULT_ACTION;
70
  Result := INET_E_DEFAULT_ACTION;
71
end;
71
end;
72
function TEmbeddedSecurityManager.GetSecurityId(pwszUrl: LPCWSTR; pbSecurityId: Pointer;
72
function TEmbeddedSecurityManager.GetSecurityId(pwszUrl: LPCWSTR; pbSecurityId: Pointer;
73
  var cbSecurityId: DWORD; dwReserved: DWORD): HResult; stdcall;
73
  var cbSecurityId: DWORD; dwReserved: DWORD): HResult; stdcall;
74
begin
74
begin
75
  Result := INET_E_DEFAULT_ACTION;
75
  Result := INET_E_DEFAULT_ACTION;
76
end;
76
end;
77
function TEmbeddedSecurityManager.ProcessUrlAction(pwszUrl: LPCWSTR; dwAction: DWORD;
77
function TEmbeddedSecurityManager.ProcessUrlAction(pwszUrl: LPCWSTR; dwAction: DWORD;
78
  pPolicy: Pointer; cbPolicy: DWORD; pContext: Pointer; cbContext: DWORD;
78
  pPolicy: Pointer; cbPolicy: DWORD; pContext: Pointer; cbContext: DWORD;
79
  dwFlags, dwReserved: DWORD): HResult; stdcall;
79
  dwFlags, dwReserved: DWORD): HResult; stdcall;
80
begin
80
begin
81
  // Result := INET_E_DEFAULT_ACTION;
81
  // Result := INET_E_DEFAULT_ACTION;
82
 
82
 
83
  // TODO: Doesn't work... Cross-Domain is still not allowed.
83
  // TODO: Doesn't work... Cross-Domain is still not allowed.
84
  PDWORD(pPolicy)^ := URLPOLICY_ALLOW;
84
  PDWORD(pPolicy)^ := URLPOLICY_ALLOW;
85
  Result := S_OK;
85
  Result := S_OK;
86
end;
86
end;
87
function TEmbeddedSecurityManager.QueryCustomPolicy(pwszUrl: LPCWSTR; const guidKey: TGUID;
87
function TEmbeddedSecurityManager.QueryCustomPolicy(pwszUrl: LPCWSTR; const guidKey: TGUID;
88
  out pPolicy: Pointer; out cbPolicy: DWORD; pContext: Pointer; cbContext: DWORD;
88
  out pPolicy: Pointer; out cbPolicy: DWORD; pContext: Pointer; cbContext: DWORD;
89
  dwReserved: DWORD): HResult; stdcall;
89
  dwReserved: DWORD): HResult; stdcall;
90
begin
90
begin
91
  // Result := INET_E_DEFAULT_ACTION;
91
  // Result := INET_E_DEFAULT_ACTION;
92
 
92
 
93
  // TODO: Doesn't work... Cross-Domain is still not allowed.
93
  // TODO: Doesn't work... Cross-Domain is still not allowed.
94
  PDWORD(pPolicy)^ := URLPOLICY_ALLOW;
94
  PDWORD(pPolicy)^ := URLPOLICY_ALLOW;
95
  Result := S_OK;
95
  Result := S_OK;
96
end;
96
end;
97
function TEmbeddedSecurityManager.SetZoneMapping(dwZone: DWORD; lpszPattern: PWideChar;
97
function TEmbeddedSecurityManager.SetZoneMapping(dwZone: DWORD; lpszPattern: PWideChar;
98
  dwFlags: DWORD): HResult; stdcall;
98
  dwFlags: DWORD): HResult; stdcall;
99
begin
99
begin
100
  Result := INET_E_DEFAULT_ACTION;
100
  Result := INET_E_DEFAULT_ACTION;
101
end;
101
end;
102
function TEmbeddedSecurityManager.GetZoneMappings(dwZone: DWORD;out ppenumString: IEnumString;
102
function TEmbeddedSecurityManager.GetZoneMappings(dwZone: DWORD;out ppenumString: IEnumString;
103
  dwFlags: DWORD): HResult; stdcall;
103
  dwFlags: DWORD): HResult; stdcall;
104
begin
104
begin
105
  Result := INET_E_DEFAULT_ACTION;
105
  Result := INET_E_DEFAULT_ACTION;
106
end;
106
end;
107
function TEmbeddedSecurityManager.MapUrlToZone(pwszUrl: LPCWSTR; out dwZone: DWORD; dwFlags: DWORD): HResult;
107
function TEmbeddedSecurityManager.MapUrlToZone(pwszUrl: LPCWSTR; out dwZone: DWORD; dwFlags: DWORD): HResult;
108
begin
108
begin
109
  dwZone := URLZONE_TRUSTED;
109
  dwZone := URLZONE_TRUSTED;
110
  Result := S_OK;
110
  Result := S_OK;
111
end;
111
end;
112
 
112
 
113
function TForm2.EmbeddedWBQueryService(const rsid, iid: TGUID; out Obj{: IInterface}): HRESULT;
113
function TForm2.EmbeddedWBQueryService(const rsid, iid: TGUID; out Obj{: IInterface}): HRESULT;
114
var
114
var
115
  sam: IInternetSecurityManager;
115
  sam: IInternetSecurityManager;
116
begin
116
begin
117
  Result := E_NOINTERFACE;
117
  Result := E_NOINTERFACE;
118
 
118
 
119
  //rsid ==> Service Identifier
119
  //rsid ==> Service Identifier
120
  //iid ==> Interface identifier
120
  //iid ==> Interface identifier
121
  if IsEqualGUID(rsid, IInternetSecurityManager) and IsEqualGUID(iid, IInternetSecurityManager) then
121
  if IsEqualGUID(rsid, IInternetSecurityManager) and IsEqualGUID(iid, IInternetSecurityManager) then
122
  begin
122
  begin
123
      sam := TEmbeddedSecurityManager.Create;
123
      sam := TEmbeddedSecurityManager.Create;
124
      IInterface(Obj) := sam;
124
      IInterface(Obj) := sam;
125
      Result := S_OK;
125
      Result := S_OK;
126
  end;
126
  end;
127
end;
127
end;
128
 
128
 
129
procedure TForm2.Timer1Timer(Sender: TObject);
129
procedure TForm2.Timer1Timer(Sender: TObject);
130
var
130
var
131
  phpScript: string;
131
  phpScript: string;
132
  sl: TStringList;
132
  sl: TStringList;
133
resourcestring
133
resourcestring
134
  SRunningScriptPleaseWait = 'Running script... please wait...';
134
  SRunningScriptPleaseWait = 'Running script... please wait...';
135
  SPleaseEnterPHPScript = 'Please enter a PHP file to execute.';
135
  SPleaseEnterPHPScript = 'Please enter a PHP file to execute.';
136
  SFileDoesNotExist = 'File %s does not exist.';
136
  SFileDoesNotExist = 'File %s does not exist.';
137
  SFastPHP = 'ViaThinkSoft FastPHP';
137
  SFastPHP = 'ViaThinkSoft FastPHP';
138
begin
138
begin
139
  Timer1.Enabled := false;
139
  Timer1.Enabled := false;
140
  phpScript := ParamStr(1);
140
  phpScript := ParamStr(1);
141
 
141
 
142
  // Remove Security
142
  // Remove Security
143
  WebBrowser1.ServiceQuery := EmbeddedWBQueryService;
143
  WebBrowser1.ServiceQuery := EmbeddedWBQueryService;
144
 
144
 
145
  WebBrowser1.LoadHTML('<h1>'+SFastPHP+'</h1>'+SRunningScriptPleaseWait);
145
  WebBrowser1.LoadHTML('<h1>'+SFastPHP+'</h1>'+SRunningScriptPleaseWait);
146
 
146
 
147
  // TODO: nice HTML error/intro pages (as resource?)
147
  // TODO: nice HTML error/intro pages (as resource?)
148
  if phpScript = '' then
148
  if phpScript = '' then
149
  begin
149
  begin
150
    WebBrowser1.LoadHTML('<h1>'+SFastPHP+'</h1>'+SPleaseEnterPHPScript);
150
    WebBrowser1.LoadHTML('<h1>'+SFastPHP+'</h1>'+SPleaseEnterPHPScript);
151
    if not OpenDialog3.Execute then
151
    if not OpenDialog3.Execute then
152
    begin
152
    begin
153
      Abort;
153
      Abort;
154
    end;
154
    end;
155
    phpScript := OpenDialog3.FileName;
155
    phpScript := OpenDialog3.FileName;
156
  end;
156
  end;
157
 
157
 
158
  if not FileExists(phpScript) then
158
  if not FileExists(phpScript) then
159
  begin
159
  begin
160
    WebBrowser1.LoadHTML(Format('<h1>'+SFastPHP+'</h1>'+SFileDoesNotExist, [phpScript]));
160
    WebBrowser1.LoadHTML(Format('<h1>'+SFastPHP+'</h1>'+SFileDoesNotExist, [phpScript]));
161
    Abort;
161
    Abort;
162
  end;
162
  end;
163
 
163
 
164
  WebBrowser1.LoadHTML(RunPHPScript(phpScript), phpScript);
164
  WebBrowser1.LoadHTML(RunPHPScript(phpScript), phpScript);
165
 
165
 
166
  Application.ProcessMessages; // This is important, otherwise the metatags can't be read...
166
  Application.ProcessMessages; // This is important, otherwise the metatags can't be read...
167
 
167
 
168
  sl := TStringList.Create;
168
  sl := TStringList.Create;
169
  try
169
  try
170
    WebBrowser1.ReadMetaTags(sl);
170
    WebBrowser1.ReadMetaTags(sl);
171
    // TODO: case insensitive
171
    // TODO: case insensitive
172
    if sl.Values['fastphp_title'] <> '' then Caption := sl.Values['fastphp_title'];
172
    if sl.Values['fastphp_title'] <> '' then Caption := sl.Values['fastphp_title'];
173
    if sl.Values['fastphp_width'] <> '' then ClientWidth := StrToInt(sl.Values['fastphp_width']);
173
    if sl.Values['fastphp_width'] <> '' then ClientWidth := StrToInt(sl.Values['fastphp_width']);
174
    if sl.Values['fastphp_height'] <> '' then ClientHeight := StrToInt(sl.Values['fastphp_height']);
174
    if sl.Values['fastphp_height'] <> '' then ClientHeight := StrToInt(sl.Values['fastphp_height']);
175
    // TODO: Add more attributes, like HTA applications had
175
    // TODO: Add more attributes, like HTA applications had
176
    // TODO: Additionally implement "HTA:APPLICATION" element, see https://docs.microsoft.com/en-us/previous-versions//ms536495%28v%3dvs.85%29
176
    // TODO: Additionally implement "HTA:APPLICATION" element, see https://docs.microsoft.com/en-us/previous-versions//ms536495%28v%3dvs.85%29
177
  finally
177
  finally
178
    FreeAndNil(sl);
178
    FreeAndNil(sl);
179
  end;
179
  end;
180
end;
180
end;
181
 
181
 
182
procedure TForm2.WebBrowser1BeforeNavigate2(ASender: TObject;
182
procedure TForm2.WebBrowser1BeforeNavigate2(ASender: TObject;
183
  const pDisp: IDispatch; const URL, Flags, TargetFrameName, PostData,
183
  const pDisp: IDispatch; const URL, Flags, TargetFrameName, PostData,
184
  Headers: OleVariant; var Cancel: WordBool);
184
  Headers: OleVariant; var Cancel: WordBool);
185
var
185
var
186
  myURL, myUrl2, getData: string;
186
  myURL, myUrl2, getData: string;
187
  p: integer;
187
  p: integer;
188
  background: boolean;
188
  background: boolean;
189
  ArgGet, ArgPost, ArgHeader: string;
189
  ArgGet, ArgPost, ArgHeader: string;
190
resourcestring
190
resourcestring
191
  SOnlyWorksInEditor = 'This action only works in FastPHP editor.';
191
  SOnlyWorksInEditor = 'This action only works in FastPHP editor.';
192
begin
192
begin
193
  background := Pos('background|', URL) >= 1; // do not translate
193
  background := Pos('background|', URL) >= 1; // do not translate
194
 
194
 
195
  {$REGION 'Line number references (PHP errors and warnings)'}
195
  {$REGION 'Line number references (PHP errors and warnings)'}
196
  if Copy(URL, 1, length(FASTPHP_GOTO_URI_PREFIX)) = FASTPHP_GOTO_URI_PREFIX then
196
  if Copy(URL, 1, length(FASTPHP_GOTO_URI_PREFIX)) = FASTPHP_GOTO_URI_PREFIX then
197
  begin
197
  begin
198
    // TODO: maybe we could even open that file in the editor!
198
    // TODO: maybe we could even open that file in the editor!
199
    ShowMessage(SOnlyWorksInEditor);
199
    ShowMessage(SOnlyWorksInEditor);
200
    Cancel := true;
200
    Cancel := true;
201
    Exit;
201
    Exit;
202
  end;
202
  end;
203
  {$ENDREGION}
203
  {$ENDREGION}
204
 
204
 
205
  {$REGION 'Intelligent browser (executes PHP scripts)'}
205
  {$REGION 'Intelligent browser (executes PHP scripts)'}
206
  if URL <> 'about:blank' then
206
  if URL <> 'about:blank' then
207
  begin
207
  begin
208
    myUrl := URL;
208
    myUrl := URL;
209
 
209
 
210
    myurl := StringReplace(myurl, 'background|', '', []); // do not translate
210
    myurl := StringReplace(myurl, 'background|', '', []); // do not translate
211
 
211
 
212
    p := Pos('?', myUrl);
212
    p := Pos('?', myUrl);
213
    if p >= 1 then
213
    if p >= 1 then
214
    begin
214
    begin
215
      getData := copy(myURL, p+1, Length(myURL)-p);
215
      getData := copy(myURL, p+1, Length(myURL)-p);
216
      myURL := copy(myURL, 1, p-1);
216
      myURL := copy(myURL, 1, p-1);
217
    end
217
    end
218
    else
218
    else
219
    begin
219
    begin
220
      getData := '';
220
      getData := '';
221
    end;
221
    end;
222
 
222
 
223
    myURL := StringReplace(myURL, 'http://wa.viathinksoft.de', '', []);
223
    myURL := StringReplace(myURL, 'http://wa.viathinksoft.de', '', []);
224
 
224
 
225
    myURL := StringReplace(myURL, 'file:///', '', []);
225
    myURL := StringReplace(myURL, 'file:///', '', []);
226
    myURL := StringReplace(myURL, '/', '\', [rfReplaceAll]);
226
    myURL := StringReplace(myURL, '/', '\', [rfReplaceAll]);
227
 
227
 
228
    // TODO: real myURL urldecode
228
    // TODO: real myURL urldecode
229
    myURL := StringReplace(myURL, '+', ' ', []);
229
    myURL := StringReplace(myURL, '+', ' ', []);
230
    myURL := StringReplace(myURL, '%20', ' ', []);
230
    myURL := StringReplace(myURL, '%20', ' ', []);
231
    myURL := StringReplace(myURL, '%%', '%', []);
231
    myURL := StringReplace(myURL, '%%', '%', []);
232
 
232
 
233
    ArgHeader := '';
233
    ArgHeader := '';
234
    ArgHeader := MyVarToStr(Headers);
234
    ArgHeader := MyVarToStr(Headers);
235
    ArgHeader := StringReplace(ArgHeader, #13, '|CR|', [rfReplaceAll]);
235
    ArgHeader := StringReplace(ArgHeader, #13, '|CR|', [rfReplaceAll]);
236
    ArgHeader := StringReplace(ArgHeader, #10, '|LF|', [rfReplaceAll]);
236
    ArgHeader := StringReplace(ArgHeader, #10, '|LF|', [rfReplaceAll]);
237
 
237
 
238
    // *.xphp is ViaThinkSoft's extension associated to FastPHPBrowser
238
    // *.xphp is ViaThinkSoft's extension associated to FastPHPBrowser
239
    // This allows the "executable PHP scripts" to be executed via double click.--
239
    // This allows the "executable PHP scripts" to be executed via double click.--
240
    if FileExists(myURL) and (EndsText('.xphp', myURL) or EndsText('.php', myURL) or EndsText('.php3', myURL) or EndsText('.php4', myURL) or EndsText('.php5', myURL) or EndsText('.phps', myURL)) then
240
    if FileExists(myURL) and (EndsText('.xphp', myURL) or EndsText('.php', myURL) or EndsText('.php3', myURL) or EndsText('.php4', myURL) or EndsText('.php5', myURL) or EndsText('.phps', myURL)) then
241
    begin
241
    begin
242
      if background then
242
      if background then
243
      begin
243
      begin
244
        // TODO: how to detach the process?
244
        // TODO: how to detach the process?
245
        ShellExecute(0, 'open', PChar(GetPHPExe), PChar('"'+myURL+'" "'+ArgGet+'" "'+ArgPost+'" "'+ArgHeader+'"'), PChar(ExtractFileDir(Application.ExeName)), SW_HIDE);
245
        ShellExecute(0, 'open', PChar(GetPHPExe), PChar('"'+myURL+'" "'+ArgGet+'" "'+ArgPost+'" "'+ArgHeader+'"'), PChar(ExtractFileDir(Application.ExeName)), SW_HIDE);
246
      end
246
      end
247
      else
247
      else
248
      begin
248
      begin
249
        // TODO: somehow prepend fastphp_server.inc.php (populates the $_GET and $_POST arrays)
249
        // TODO: somehow prepend fastphp_server.inc.php (populates the $_GET and $_POST arrays)
250
        // TODO: is there a maximal length for the command line?
250
        // TODO: is there a maximal length for the command line?
251
        ArgGet := MyVarToStr(getData);
251
        ArgGet := MyVarToStr(getData);
252
        ArgPost := MyVarToStr(PostData);
252
        ArgPost := MyVarToStr(PostData);
253
 
253
 
254
        myUrl2 := myUrl;
254
        myUrl2 := myUrl;
255
        myUrl2 := StringReplace(myUrl2, '\', '/', [rfReplaceAll]);
255
        myUrl2 := StringReplace(myUrl2, '\', '/', [rfReplaceAll]);
256
        // TODO: real myURL urlencode
256
        // TODO: real myURL urlencode
257
        myUrl2 := StringReplace(myUrl2, '%', '%%', []);
257
        myUrl2 := StringReplace(myUrl2, '%', '%%', []);
258
        //myUrl2 := StringReplace(myUrl2, ' ', '%20', []);
258
        //myUrl2 := StringReplace(myUrl2, ' ', '%20', []);
259
        myUrl2 := StringReplace(myUrl2, ' ', '+', []);
259
        myUrl2 := StringReplace(myUrl2, ' ', '+', []);
260
        myUrl2 := 'http://wa.viathinksoft.de/' + myUrl2;
260
        myUrl2 := 'http://wa.viathinksoft.de/' + myUrl2;
261
 
261
 
262
        // showmessage(myUrl2);
262
        // showmessage(myUrl2);
263
        WebBrowser1.LoadHTML(GetDosOutput('"'+GetPHPExe+'" -f "'+myURL+'" -- "'+ArgGet+'" "'+ArgPost+'" "'+ArgHeader+'"', ExtractFileDir(Application.ExeName)), myUrl2);
263
        WebBrowser1.LoadHTML(GetDosOutput('"'+GetPHPExe+'" -f "'+myURL+'" -- "'+ArgGet+'" "'+ArgPost+'" "'+ArgHeader+'"', ExtractFileDir(Application.ExeName)), myUrl2);
264
      end;
264
      end;
265
      Cancel := true;
265
      Cancel := true;
266
    end;
266
    end;
267
  end;
267
  end;
268
  {$ENDREGION}
268
  {$ENDREGION}
269
end;
269
end;
270
 
270
 
271
procedure TForm2.WebBrowser1WindowClosing(ASender: TObject;
271
procedure TForm2.WebBrowser1WindowClosing(ASender: TObject;
272
  IsChildWindow: WordBool; var Cancel: WordBool);
272
  IsChildWindow: WordBool; var Cancel: WordBool);
273
begin
273
begin
274
  Close;
274
  Close;
275
  Cancel := true;
275
  Cancel := true;
276
end;
276
end;
277
 
277
 
278
end.
278
end.
279
 
279