WinLauncher.cpp 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706
  1. /*
  2. * Copyright (C) 2006, 2008 Apple Computer, Inc. All rights reserved.
  3. * Copyright (C) 2009, 2011 Brent Fulgham. All rights reserved.
  4. * Copyright (C) 2009, 2010, 2011 Appcelerator, Inc. All rights reserved.
  5. *
  6. * Redistribution and use in source and binary forms, with or without
  7. * modification, are permitted provided that the following conditions
  8. * are met:
  9. * 1. Redistributions of source code must retain the above copyright
  10. * notice, this list of conditions and the following disclaimer.
  11. * 2. Redistributions in binary form must reproduce the above copyright
  12. * notice, this list of conditions and the following disclaimer in the
  13. * documentation and/or other materials provided with the distribution.
  14. *
  15. * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
  16. * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  17. * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
  18. * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
  19. * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
  20. * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
  21. * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  22. * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
  23. * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  24. * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  25. * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  26. */
  27. #include "stdafx.h"
  28. #include "WinLauncher.h"
  29. #include "DOMDefaultImpl.h"
  30. #include "PrintWebUIDelegate.h"
  31. #include <WebKit/WebKitCOMAPI.h>
  32. #include <wtf/Platform.h>
  33. #if USE(CF)
  34. #include <CoreFoundation/CFPriv.h>
  35. #include <CoreFoundation/CFRunLoop.h>
  36. #endif
  37. #include <assert.h>
  38. #include <commctrl.h>
  39. #include <commdlg.h>
  40. #include <objbase.h>
  41. #include <shellapi.h>
  42. #include <shlwapi.h>
  43. #include <string>
  44. #include <wininet.h>
  45. #define MAX_LOADSTRING 100
  46. #define URLBAR_HEIGHT 24
  47. // Global Variables:
  48. HINSTANCE hInst; // current instance
  49. HWND hMainWnd;
  50. HWND hURLBarWnd;
  51. WNDPROC DefEditProc = 0;
  52. WNDPROC DefWebKitProc = 0;
  53. IWebView* gWebView = 0;
  54. IWebViewPrivate* gWebViewPrivate = 0;
  55. HWND gViewWindow = 0;
  56. WinLauncherWebHost* gWebHost = 0;
  57. PrintWebUIDelegate* gPrintDelegate = 0;
  58. TCHAR szTitle[MAX_LOADSTRING]; // The title bar text
  59. TCHAR szWindowClass[MAX_LOADSTRING]; // the main window class name
  60. // Support moving the transparent window
  61. POINT s_windowPosition = { 100, 100 };
  62. SIZE s_windowSize = { 800, 400 };
  63. bool s_usesLayeredWebView = false;
  64. bool s_fullDesktop = false;
  65. // Forward declarations of functions included in this code module:
  66. ATOM MyRegisterClass(HINSTANCE hInstance);
  67. LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
  68. INT_PTR CALLBACK About(HWND, UINT, WPARAM, LPARAM);
  69. LRESULT CALLBACK MyEditProc(HWND, UINT, WPARAM, LPARAM);
  70. static void loadURL(BSTR urlBStr);
  71. static bool usesLayeredWebView()
  72. {
  73. return s_usesLayeredWebView;
  74. }
  75. static bool shouldUseFullDesktop()
  76. {
  77. return s_fullDesktop;
  78. }
  79. class SimpleEventListener : public DOMEventListener {
  80. public:
  81. SimpleEventListener(LPWSTR type)
  82. {
  83. wcsncpy_s(m_eventType, 100, type, 100);
  84. m_eventType[99] = 0;
  85. }
  86. virtual HRESULT STDMETHODCALLTYPE handleEvent(IDOMEvent* evt)
  87. {
  88. wchar_t message[255];
  89. wcscpy_s(message, 255, m_eventType);
  90. wcscat_s(message, 255, L" event fired!");
  91. ::MessageBox(0, message, L"Event Handler", MB_OK);
  92. return S_OK;
  93. }
  94. private:
  95. wchar_t m_eventType[100];
  96. };
  97. HRESULT WinLauncherWebHost::updateAddressBar(IWebView* webView)
  98. {
  99. IWebFrame* mainFrame = 0;
  100. IWebDataSource* dataSource = 0;
  101. IWebMutableURLRequest* request = 0;
  102. BSTR frameURL = 0;
  103. HRESULT hr = S_OK;
  104. hr = webView->mainFrame(&mainFrame);
  105. if (FAILED(hr))
  106. goto exit;
  107. hr = mainFrame->dataSource(&dataSource);
  108. if (FAILED(hr) || !dataSource)
  109. hr = mainFrame->provisionalDataSource(&dataSource);
  110. if (FAILED(hr) || !dataSource)
  111. goto exit;
  112. hr = dataSource->request(&request);
  113. if (FAILED(hr) || !request)
  114. goto exit;
  115. hr = request->mainDocumentURL(&frameURL);
  116. if (FAILED(hr))
  117. goto exit;
  118. SendMessage(hURLBarWnd, (UINT)WM_SETTEXT, 0, (LPARAM)frameURL);
  119. exit:
  120. if (mainFrame)
  121. mainFrame->Release();
  122. if (dataSource)
  123. dataSource->Release();
  124. if (request)
  125. request->Release();
  126. SysFreeString(frameURL);
  127. return 0;
  128. }
  129. HRESULT STDMETHODCALLTYPE WinLauncherWebHost::didFailProvisionalLoadWithError(IWebView*, IWebError *error, IWebFrame*)
  130. {
  131. BSTR errorDescription = 0;
  132. HRESULT hr = error->localizedDescription(&errorDescription);
  133. if (FAILED(hr))
  134. errorDescription = L"Failed to load page and to localize error description.";
  135. ::MessageBoxW(0, static_cast<LPCWSTR>(errorDescription), L"Error", MB_APPLMODAL | MB_OK);
  136. if (SUCCEEDED(hr))
  137. SysFreeString(errorDescription);
  138. return S_OK;
  139. }
  140. HRESULT STDMETHODCALLTYPE WinLauncherWebHost::QueryInterface(REFIID riid, void** ppvObject)
  141. {
  142. *ppvObject = 0;
  143. if (IsEqualGUID(riid, IID_IUnknown))
  144. *ppvObject = static_cast<IWebFrameLoadDelegate*>(this);
  145. else if (IsEqualGUID(riid, IID_IWebFrameLoadDelegate))
  146. *ppvObject = static_cast<IWebFrameLoadDelegate*>(this);
  147. else
  148. return E_NOINTERFACE;
  149. AddRef();
  150. return S_OK;
  151. }
  152. ULONG STDMETHODCALLTYPE WinLauncherWebHost::AddRef(void)
  153. {
  154. return ++m_refCount;
  155. }
  156. ULONG STDMETHODCALLTYPE WinLauncherWebHost::Release(void)
  157. {
  158. ULONG newRef = --m_refCount;
  159. if (!newRef)
  160. delete(this);
  161. return newRef;
  162. }
  163. HRESULT WinLauncherWebHost::didFinishLoadForFrame(IWebView* webView, IWebFrame* frame)
  164. {
  165. IDOMDocument* doc = 0;
  166. frame->DOMDocument(&doc);
  167. IDOMElement* element = 0;
  168. IDOMEventTarget* target = 0;
  169. HRESULT hr = doc->getElementById(L"webkit logo", &element);
  170. if (!SUCCEEDED(hr))
  171. goto exit;
  172. hr = element->QueryInterface(IID_IDOMEventTarget, reinterpret_cast<void**>(&target));
  173. if (!SUCCEEDED(hr))
  174. goto exit;
  175. hr = target->addEventListener(L"click", new SimpleEventListener (L"webkit logo click"), FALSE);
  176. if (!SUCCEEDED(hr))
  177. goto exit;
  178. exit:
  179. if (target)
  180. target->Release();
  181. if (element)
  182. element->Release();
  183. if (doc)
  184. doc->Release();
  185. return hr;
  186. }
  187. static void resizeSubViews()
  188. {
  189. if (usesLayeredWebView() || !gViewWindow)
  190. return;
  191. RECT rcClient;
  192. GetClientRect(hMainWnd, &rcClient);
  193. MoveWindow(hURLBarWnd, 0, 0, rcClient.right, URLBAR_HEIGHT, TRUE);
  194. MoveWindow(gViewWindow, 0, URLBAR_HEIGHT, rcClient.right, rcClient.bottom - URLBAR_HEIGHT, TRUE);
  195. }
  196. static void subclassForLayeredWindow()
  197. {
  198. hMainWnd = gViewWindow;
  199. #if defined _M_AMD64 || defined _WIN64
  200. DefWebKitProc = reinterpret_cast<WNDPROC>(::GetWindowLongPtr(hMainWnd, GWLP_WNDPROC));
  201. ::SetWindowLongPtr(hMainWnd, GWLP_WNDPROC, reinterpret_cast<LONG_PTR>(WndProc));
  202. #else
  203. DefWebKitProc = reinterpret_cast<WNDPROC>(::GetWindowLong(hMainWnd, GWL_WNDPROC));
  204. ::SetWindowLong(hMainWnd, GWL_WNDPROC, reinterpret_cast<LONG_PTR>(WndProc));
  205. #endif
  206. }
  207. static void computeFullDesktopFrame()
  208. {
  209. RECT desktop;
  210. if (!::SystemParametersInfo(SPI_GETWORKAREA, 0, static_cast<void*>(&desktop), 0))
  211. return;
  212. s_windowPosition.x = 0;
  213. s_windowPosition.y = 0;
  214. s_windowSize.cx = desktop.right - desktop.left;
  215. s_windowSize.cy = desktop.bottom - desktop.top;
  216. }
  217. BOOL WINAPI DllMain(HINSTANCE dllInstance, DWORD reason, LPVOID)
  218. {
  219. if (reason == DLL_PROCESS_ATTACH)
  220. hInst = dllInstance;
  221. return TRUE;
  222. }
  223. extern "C" __declspec(dllexport) int WINAPI dllLauncherEntryPoint(HINSTANCE, HINSTANCE, LPTSTR, int nCmdShow)
  224. {
  225. #ifdef _CRTDBG_MAP_ALLOC
  226. _CrtSetReportFile(_CRT_WARN, _CRTDBG_FILE_STDERR);
  227. _CrtSetReportMode(_CRT_WARN, _CRTDBG_MODE_FILE);
  228. #endif
  229. // TODO: Place code here.
  230. MSG msg = {0};
  231. HACCEL hAccelTable;
  232. INITCOMMONCONTROLSEX InitCtrlEx;
  233. InitCtrlEx.dwSize = sizeof(INITCOMMONCONTROLSEX);
  234. InitCtrlEx.dwICC = 0x00004000; //ICC_STANDARD_CLASSES;
  235. InitCommonControlsEx(&InitCtrlEx);
  236. BSTR requestedURL = 0;
  237. int argc = 0;
  238. WCHAR** argv = CommandLineToArgvW(GetCommandLineW(), &argc);
  239. for (int i = 1; i < argc; ++i) {
  240. if (!wcsicmp(argv[i], L"--transparent"))
  241. s_usesLayeredWebView = true;
  242. else if (!wcsicmp(argv[i], L"--desktop"))
  243. s_fullDesktop = true;
  244. else if (!requestedURL)
  245. requestedURL = ::SysAllocString(argv[i]);
  246. }
  247. // Initialize global strings
  248. LoadString(hInst, IDS_APP_TITLE, szTitle, MAX_LOADSTRING);
  249. LoadString(hInst, IDC_WINLAUNCHER, szWindowClass, MAX_LOADSTRING);
  250. MyRegisterClass(hInst);
  251. if (shouldUseFullDesktop())
  252. computeFullDesktopFrame();
  253. // Init COM
  254. OleInitialize(NULL);
  255. if (usesLayeredWebView()) {
  256. hURLBarWnd = CreateWindow(L"EDIT", L"Type URL Here",
  257. WS_OVERLAPPEDWINDOW | WS_VISIBLE | WS_BORDER | ES_LEFT | ES_AUTOVSCROLL,
  258. s_windowPosition.x, s_windowPosition.y + s_windowSize.cy, s_windowSize.cx, URLBAR_HEIGHT,
  259. 0,
  260. 0,
  261. hInst, 0);
  262. } else {
  263. hMainWnd = CreateWindow(szWindowClass, szTitle, WS_OVERLAPPEDWINDOW,
  264. CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, 0, 0, hInst, 0);
  265. if (!hMainWnd)
  266. return FALSE;
  267. hURLBarWnd = CreateWindow(L"EDIT", 0,
  268. WS_CHILD | WS_VISIBLE | WS_BORDER | ES_LEFT | ES_AUTOVSCROLL,
  269. 0, 0, 0, 0,
  270. hMainWnd,
  271. 0,
  272. hInst, 0);
  273. ShowWindow(hMainWnd, nCmdShow);
  274. UpdateWindow(hMainWnd);
  275. }
  276. #if defined _M_AMD64 || defined _WIN64
  277. DefEditProc = reinterpret_cast<WNDPROC>(GetWindowLongPtr(hURLBarWnd, GWLP_WNDPROC));
  278. SetWindowLongPtr(hURLBarWnd, GWLP_WNDPROC, reinterpret_cast<LONG_PTR>(MyEditProc));
  279. #else
  280. DefEditProc = reinterpret_cast<WNDPROC>(GetWindowLong(hURLBarWnd, GWL_WNDPROC));
  281. SetWindowLong(hURLBarWnd, GWL_WNDPROC, reinterpret_cast<LONG_PTR>(MyEditProc));
  282. #endif
  283. SetFocus(hURLBarWnd);
  284. RECT clientRect = { s_windowPosition.x, s_windowPosition.y, s_windowPosition.x + s_windowSize.cx, s_windowPosition.y + s_windowSize.cy };
  285. IWebPreferences* tmpPreferences = 0;
  286. IWebPreferences* standardPreferences = 0;
  287. if (FAILED(WebKitCreateInstance(CLSID_WebPreferences, 0, IID_IWebPreferences, reinterpret_cast<void**>(&tmpPreferences))))
  288. goto exit;
  289. if (FAILED(tmpPreferences->standardPreferences(&standardPreferences)))
  290. goto exit;
  291. standardPreferences->setAcceleratedCompositingEnabled(TRUE);
  292. IWebPreferencesPrivate* prefsPrivate = 0;
  293. HRESULT hr = standardPreferences->QueryInterface(IID_IWebPreferencesPrivate, reinterpret_cast<void**>(&prefsPrivate));
  294. if (SUCCEEDED(hr))
  295. prefsPrivate->setFullScreenEnabled(TRUE);
  296. hr = WebKitCreateInstance(CLSID_WebView, 0, IID_IWebView, reinterpret_cast<void**>(&gWebView));
  297. if (FAILED(hr))
  298. goto exit;
  299. hr = gWebView->QueryInterface(IID_IWebViewPrivate, reinterpret_cast<void**>(&gWebViewPrivate));
  300. if (FAILED(hr))
  301. goto exit;
  302. gWebHost = new WinLauncherWebHost();
  303. gWebHost->AddRef();
  304. hr = gWebView->setFrameLoadDelegate(gWebHost);
  305. if (FAILED(hr))
  306. goto exit;
  307. gPrintDelegate = new PrintWebUIDelegate;
  308. gPrintDelegate->AddRef();
  309. hr = gWebView->setUIDelegate(gPrintDelegate);
  310. if (FAILED (hr))
  311. goto exit;
  312. hr = gWebView->setHostWindow(reinterpret_cast<OLE_HANDLE>(hMainWnd));
  313. if (FAILED(hr))
  314. goto exit;
  315. hr = gWebView->initWithFrame(clientRect, 0, 0);
  316. if (FAILED(hr))
  317. goto exit;
  318. if (!requestedURL) {
  319. IWebFrame* frame;
  320. hr = gWebView->mainFrame(&frame);
  321. if (FAILED(hr))
  322. goto exit;
  323. static BSTR defaultHTML = SysAllocString(TEXT("<p style=\"background-color: #00FF00\">Testing</p><img id=\"webkit logo\" src=\"http://webkit.org/images/icon-gold.png\" alt=\"Face\"><div style=\"border: solid blue; background: white;\" contenteditable=\"true\">div with blue border</div><ul><li>foo<li>bar<li>baz</ul>"));
  324. frame->loadHTMLString(defaultHTML, 0);
  325. frame->Release();
  326. }
  327. hr = gWebViewPrivate->setTransparent(usesLayeredWebView());
  328. if (FAILED(hr))
  329. goto exit;
  330. hr = gWebViewPrivate->setUsesLayeredWindow(usesLayeredWebView());
  331. if (FAILED(hr))
  332. goto exit;
  333. hr = gWebViewPrivate->viewWindow(reinterpret_cast<OLE_HANDLE*>(&gViewWindow));
  334. if (FAILED(hr) || !gViewWindow)
  335. goto exit;
  336. if (usesLayeredWebView())
  337. subclassForLayeredWindow();
  338. resizeSubViews();
  339. ShowWindow(gViewWindow, nCmdShow);
  340. UpdateWindow(gViewWindow);
  341. hAccelTable = LoadAccelerators(hInst, MAKEINTRESOURCE(IDC_WINLAUNCHER));
  342. if (requestedURL) {
  343. loadURL(requestedURL);
  344. ::SysFreeString(requestedURL);
  345. requestedURL = 0;
  346. }
  347. // Main message loop:
  348. #if USE(CF)
  349. _CFRunLoopSetWindowsMessageQueueMask(CFRunLoopGetMain(), QS_ALLINPUT | QS_ALLPOSTMESSAGE, kCFRunLoopDefaultMode);
  350. CFRunLoopRun();
  351. #else
  352. while (GetMessage(&msg, NULL, 0, 0)) {
  353. if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg)) {
  354. TranslateMessage(&msg);
  355. DispatchMessage(&msg);
  356. }
  357. }
  358. #endif
  359. exit:
  360. gPrintDelegate->Release();
  361. if (gWebViewPrivate)
  362. gWebViewPrivate->Release();
  363. gWebView->Release();
  364. if (standardPreferences)
  365. standardPreferences->Release();
  366. tmpPreferences->Release();
  367. shutDownWebKit();
  368. #ifdef _CRTDBG_MAP_ALLOC
  369. _CrtDumpMemoryLeaks();
  370. #endif
  371. // Shut down COM.
  372. OleUninitialize();
  373. return static_cast<int>(msg.wParam);
  374. }
  375. ATOM MyRegisterClass(HINSTANCE hInstance)
  376. {
  377. WNDCLASSEX wcex;
  378. wcex.cbSize = sizeof(WNDCLASSEX);
  379. wcex.style = CS_HREDRAW | CS_VREDRAW;
  380. wcex.lpfnWndProc = WndProc;
  381. wcex.cbClsExtra = 0;
  382. wcex.cbWndExtra = 0;
  383. wcex.hInstance = hInstance;
  384. wcex.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_WINLAUNCHER));
  385. wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
  386. wcex.hbrBackground = 0;
  387. wcex.lpszMenuName = MAKEINTRESOURCE(IDC_WINLAUNCHER);
  388. wcex.lpszClassName = szWindowClass;
  389. wcex.hIconSm = LoadIcon(wcex.hInstance, MAKEINTRESOURCE(IDI_SMALL));
  390. return RegisterClassEx(&wcex);
  391. }
  392. static BOOL CALLBACK AbortProc(HDC hDC, int Error)
  393. {
  394. MSG msg;
  395. while (::PeekMessage(&msg, 0, 0, 0, PM_REMOVE)) {
  396. ::TranslateMessage(&msg);
  397. ::DispatchMessage(&msg);
  398. }
  399. return TRUE;
  400. }
  401. static HDC getPrinterDC()
  402. {
  403. PRINTDLG pdlg;
  404. memset(&pdlg, 0, sizeof(PRINTDLG));
  405. pdlg.lStructSize = sizeof(PRINTDLG);
  406. pdlg.Flags = PD_PRINTSETUP | PD_RETURNDC;
  407. ::PrintDlg(&pdlg);
  408. return pdlg.hDC;
  409. }
  410. static void initDocStruct(DOCINFO* di, TCHAR* docname)
  411. {
  412. memset(di, 0, sizeof(DOCINFO));
  413. di->cbSize = sizeof(DOCINFO);
  414. di->lpszDocName = docname;
  415. }
  416. void PrintView(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
  417. {
  418. HDC printDC = getPrinterDC();
  419. if (!printDC) {
  420. ::MessageBoxW(0, L"Error creating printing DC", L"Error", MB_APPLMODAL | MB_OK);
  421. return;
  422. }
  423. if (::SetAbortProc(printDC, AbortProc) == SP_ERROR) {
  424. ::MessageBoxW(0, L"Error setting up AbortProc", L"Error", MB_APPLMODAL | MB_OK);
  425. return;
  426. }
  427. IWebFrame* frame = 0;
  428. IWebFramePrivate* framePrivate = 0;
  429. if (FAILED(gWebView->mainFrame(&frame)))
  430. goto exit;
  431. if (FAILED(frame->QueryInterface(&framePrivate)))
  432. goto exit;
  433. framePrivate->setInPrintingMode(TRUE, printDC);
  434. UINT pageCount = 0;
  435. framePrivate->getPrintedPageCount(printDC, &pageCount);
  436. DOCINFO di;
  437. initDocStruct(&di, L"WebKit Doc");
  438. ::StartDoc(printDC, &di);
  439. // FIXME: Need CoreGraphics implementation
  440. void* graphicsContext = 0;
  441. for (size_t page = 1; page <= pageCount; ++page) {
  442. ::StartPage(printDC);
  443. framePrivate->spoolPages(printDC, page, page, graphicsContext);
  444. ::EndPage(printDC);
  445. }
  446. framePrivate->setInPrintingMode(FALSE, printDC);
  447. ::EndDoc(printDC);
  448. ::DeleteDC(printDC);
  449. exit:
  450. if (frame)
  451. frame->Release();
  452. if (framePrivate)
  453. framePrivate->Release();
  454. }
  455. static const int dragBarHeight = 30;
  456. LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
  457. {
  458. WNDPROC parentProc = usesLayeredWebView() ? DefWebKitProc : DefWindowProc;
  459. switch (message) {
  460. case WM_NCHITTEST:
  461. if (usesLayeredWebView()) {
  462. RECT window;
  463. ::GetWindowRect(hWnd, &window);
  464. // For testing our transparent window, we need a region to use as a handle for
  465. // dragging. The right way to do this would be to query the web view to see what's
  466. // under the mouse. However, for testing purposes we just use an arbitrary
  467. // 30 pixel band at the top of the view as an arbitrary gripping location.
  468. //
  469. // When we are within this bad, return HT_CAPTION to tell Windows we want to
  470. // treat this region as if it were the title bar on a normal window.
  471. int y = HIWORD(lParam);
  472. if ((y > window.top) && (y < window.top + dragBarHeight))
  473. return HTCAPTION;
  474. }
  475. return CallWindowProc(parentProc, hWnd, message, wParam, lParam);
  476. case WM_COMMAND: {
  477. int wmId = LOWORD(wParam);
  478. int wmEvent = HIWORD(wParam);
  479. // Parse the menu selections:
  480. switch (wmId) {
  481. case IDM_ABOUT:
  482. DialogBox(hInst, MAKEINTRESOURCE(IDD_ABOUTBOX), hWnd, About);
  483. break;
  484. case IDM_EXIT:
  485. DestroyWindow(hWnd);
  486. break;
  487. case IDM_PRINT:
  488. PrintView(hWnd, message, wParam, lParam);
  489. break;
  490. default:
  491. return CallWindowProc(parentProc, hWnd, message, wParam, lParam);
  492. }
  493. }
  494. break;
  495. case WM_DESTROY:
  496. PostQuitMessage(0);
  497. break;
  498. case WM_SIZE:
  499. if (!gWebView || usesLayeredWebView())
  500. return CallWindowProc(parentProc, hWnd, message, wParam, lParam);
  501. resizeSubViews();
  502. break;
  503. default:
  504. return CallWindowProc(parentProc, hWnd, message, wParam, lParam);
  505. }
  506. return 0;
  507. }
  508. #define MAX_URL_LENGTH 1024
  509. LRESULT CALLBACK MyEditProc(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
  510. {
  511. switch (message) {
  512. case WM_CHAR:
  513. if (wParam == 13) { // Enter Key
  514. wchar_t strPtr[MAX_URL_LENGTH];
  515. *((LPWORD)strPtr) = MAX_URL_LENGTH;
  516. int strLen = SendMessage(hDlg, EM_GETLINE, 0, (LPARAM)strPtr);
  517. BSTR bstr = SysAllocStringLen(strPtr, strLen);
  518. loadURL(bstr);
  519. SysFreeString(bstr);
  520. return 0;
  521. } else
  522. return (LRESULT)CallWindowProc((WNDPROC)DefEditProc,hDlg,message,wParam,lParam);
  523. break;
  524. default:
  525. return (LRESULT)CallWindowProc((WNDPROC)DefEditProc,hDlg,message,wParam,lParam);
  526. break;
  527. }
  528. }
  529. // Message handler for about box.
  530. INT_PTR CALLBACK About(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
  531. {
  532. UNREFERENCED_PARAMETER(lParam);
  533. switch (message) {
  534. case WM_INITDIALOG:
  535. return (INT_PTR)TRUE;
  536. case WM_COMMAND:
  537. if (LOWORD(wParam) == IDOK || LOWORD(wParam) == IDCANCEL) {
  538. EndDialog(hDlg, LOWORD(wParam));
  539. return (INT_PTR)TRUE;
  540. }
  541. break;
  542. }
  543. return (INT_PTR)FALSE;
  544. }
  545. static void loadURL(BSTR urlBStr)
  546. {
  547. IWebFrame* frame = 0;
  548. IWebMutableURLRequest* request = 0;
  549. static BSTR methodBStr = SysAllocString(TEXT("GET"));
  550. if (urlBStr && urlBStr[0] && (PathFileExists(urlBStr) || PathIsUNC(urlBStr))) {
  551. TCHAR fileURL[INTERNET_MAX_URL_LENGTH];
  552. DWORD fileURLLength = sizeof(fileURL)/sizeof(fileURL[0]);
  553. if (SUCCEEDED(UrlCreateFromPath(urlBStr, fileURL, &fileURLLength, 0)))
  554. SysReAllocString(&urlBStr, fileURL);
  555. }
  556. HRESULT hr = gWebView->mainFrame(&frame);
  557. if (FAILED(hr))
  558. goto exit;
  559. hr = WebKitCreateInstance(CLSID_WebMutableURLRequest, 0, IID_IWebMutableURLRequest, (void**)&request);
  560. if (FAILED(hr))
  561. goto exit;
  562. hr = request->initWithURL(urlBStr, WebURLRequestUseProtocolCachePolicy, 60);
  563. if (FAILED(hr))
  564. goto exit;
  565. hr = request->setHTTPMethod(methodBStr);
  566. if (FAILED(hr))
  567. goto exit;
  568. hr = frame->loadRequest(request);
  569. if (FAILED(hr))
  570. goto exit;
  571. SetFocus(gViewWindow);
  572. exit:
  573. if (frame)
  574. frame->Release();
  575. if (request)
  576. request->Release();
  577. }