[原创]升级SOUI WKE以支持_blank

由于WKE的精简模式,导致原有的SOUI不支持针对诸多内容的调用,此处针对WKE的部分内容做升级,以支持对应的功能。

目的:使WKE可以_blank弹出新窗口。

由国人 海绵宝宝维护的WKE新分支:https://github.com/cexer/wke 

编译新WKE的方式很简单:

1、下载master,并解压缩,如果有git就自己clone一下就好了

2、运行根目录下的vs2008.bat,打开后直接编译即可,时间根据CPU不同而不同。

SOUI的模式是动态加载函数,所以参考一下WKE头文件,即可完成函数调用。

特别注意,SOUI的WKE.DLL中已经将WKE封装为类,此处的WKE.DLL内是纯C函数,无类,所以我们要自己写。

如果懒得自己写动态接口,就直接引用WKE.H就好了,然后连接一下WKE.LIB(这样只是不太好剥离或按目录加载库)。

由于本人巨懒,懒癌晚期,所以我直接引用lib了,哈哈哈。

 

直接上点干货

  1 /*!
  2  * \file SWkeWebkitEx.h
  3  * \date 2016/04/12 14:31
  4  *
  5  * \author koangel
  6  * Contact: jackliu100@gmail.com
  7  *
  8  * \brief 针对新版本WKE的封装,使用C函数版本
  9  *
 10  * 为了区分改为SWkeWbkitEx名,与之前版本不冲突。
 11 */
 12 #pragma once
 13 #include <wke.h>
 14 
 15 #pragma comment(lib,"wke.lib")
 16 
 17 namespace SOUI
 18 {
 19     // 此处改为自己渲染程序
 20     class SWkeRenderGDI
 21     {
 22     public:
 23         SWkeRenderGDI()
 24             :m_hView(NULL)
 25             , m_hDC(NULL)
 26             , m_hBitmap(NULL)
 27             , m_pixels(NULL)
 28             , m_width(0)
 29             , m_height(0)
 30         {
 31         }
 32 
 33         virtual ~SWkeRenderGDI()
 34         {
 35             if (m_hDC)
 36                 DeleteDC(m_hDC);
 37 
 38             if (m_hBitmap)
 39                 DeleteObject(m_hBitmap);
 40         }
 41 
 42         virtual bool init(HWND hView)
 43         {
 44             m_hView = hView;
 45             m_hDC = CreateCompatibleDC(0);
 46 
 47             RECT rect;
 48             GetClientRect(hView, &rect);
 49             resize(rect.right, rect.bottom);
 50             return true;
 51         }
 52 
 53         virtual void destroy()
 54         {
 55             delete this;
 56         }
 57 
 58         virtual void resize(unsigned int w, unsigned int h)
 59         {
 60             if (m_width == w && m_height == h)
 61                 return;
 62 
 63             m_width = w;
 64             m_height = h;
 65             m_pixels = NULL;
 66         }
 67 
 68         virtual void render(wkeWebView webView)
 69         {
 70             if (wkeIsDirty(webView))
 71             {
 72                 if (m_pixels == NULL)
 73                     createBitmap();
 74 
 75                 wkePaint2(webView, m_pixels, 0);
 76 
 77                 HDC hDC = GetDC(m_hView);
 78                 BitBlt(hDC, 0, 0, m_width, m_height, m_hDC, 0, 0, SRCCOPY);
 79                 ReleaseDC(m_hView, hDC);
 80             }
 81         }
 82 
 83         void createBitmap()
 84         {
 85             BITMAPINFO bi;
 86             memset(&bi, 0, sizeof(bi));
 87             bi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
 88             bi.bmiHeader.biWidth = int(m_width);
 89             bi.bmiHeader.biHeight = -int(m_height);
 90             bi.bmiHeader.biPlanes = 1;
 91             bi.bmiHeader.biBitCount = 32;
 92             bi.bmiHeader.biCompression = BI_RGB;
 93 
 94             HBITMAP hbmp = ::CreateDIBSection(0, &bi, DIB_RGB_COLORS, &m_pixels, NULL, 0);
 95 
 96             SelectObject(m_hDC, hbmp);
 97 
 98             if (m_hBitmap)
 99                 DeleteObject(m_hBitmap);
100 
101             m_hBitmap = hbmp;
102         }
103 
104     private:
105         HWND m_hView;
106         HBITMAP m_hBitmap;
107         HDC m_hDC;
108         unsigned int m_width;
109         unsigned int m_height;
110         void* m_pixels;
111     };
112 
113     const char TM_TICKER = 1;
114     class SWkeWebkitEx :
115         public SWindow,protected IIdleHandler
116     {
117         SOUI_CLASS_NAME(SWkeWebkit, L"wkeWebkit")
118     public:
119         SWkeWebkitEx();
120         virtual ~SWkeWebkitEx();
121 
122         // 初始化WKE
123         static void SWkeInit();
124         // 销毁WKE
125         static void SWkeFinalize();
126 
127         wkeWebView    GetWebView() { return m_pWebView; }
128     protected:
129         virtual BOOL OnIdle();
130     protected:
131         int OnCreate(void *);
132         void OnDestroy();
133         void OnPaint(IRenderTarget *pRT);
134         void OnSize(UINT nType, CSize size);
135         LRESULT OnMouseEvent(UINT uMsg, WPARAM wParam, LPARAM lParam);
136         LRESULT OnMouseWheel(UINT uMsg, WPARAM wParam, LPARAM lParam);
137         LRESULT OnKeyDown(UINT uMsg, WPARAM wParam, LPARAM lParam);
138         LRESULT OnKeyUp(UINT uMsg, WPARAM wParam, LPARAM lParam);
139         LRESULT OnChar(UINT uMsg, WPARAM wParam, LPARAM lParam);
140         LRESULT OnImeStartComposition(UINT uMsg, WPARAM wParam, LPARAM lParam);
141         void OnSetFocus();
142         void OnKillFocus();
143         void OnTimer(char cTimerID);
144 
145         virtual BOOL OnSetCursor(const CPoint &pt);
146         virtual UINT OnGetDlgCode() { return SC_WANTALLKEYS; }
147         BOOL OnAttrUrl(SStringW strValue, BOOL bLoading);
148         SOUI_ATTRS_BEGIN()
149             ATTR_CUSTOM(L"url", OnAttrUrl)
150             SOUI_ATTRS_END()
151 
152             SOUI_MSG_MAP_BEGIN()
153             MSG_WM_PAINT_EX(OnPaint)
154             MSG_WM_CREATE(OnCreate)
155             MSG_WM_DESTROY(OnDestroy)
156             MSG_WM_SIZE(OnSize)
157             MSG_WM_TIMER_EX(OnTimer)
158             MSG_WM_SETFOCUS_EX(OnSetFocus)
159             MSG_WM_KILLFOCUS_EX(OnKillFocus)
160             MESSAGE_RANGE_HANDLER_EX(WM_MOUSEFIRST, 0x209, OnMouseEvent)
161             MESSAGE_HANDLER_EX(WM_MOUSEWHEEL, OnMouseWheel)
162             MESSAGE_HANDLER_EX(WM_KEYDOWN, OnKeyDown)
163             MESSAGE_HANDLER_EX(WM_KEYUP, OnKeyUp)
164             MESSAGE_HANDLER_EX(WM_CHAR, OnChar)
165             MESSAGE_HANDLER_EX(WM_IME_STARTCOMPOSITION, OnImeStartComposition)
166             SOUI_MSG_MAP_END()
167     protected:
168         wkeWebView m_pWebView;
169         SStringW m_strUrl;
170         SWkeRenderGDI m_render;
171 
172         static wkeWebView onCreateView(wkeWebView webView, void* param, const wkeNewViewInfo* info);
173     };
174 }

Cpp部分代码

  1 /*!
  2 * \file SWkeWebkitEx.cpp
  3 * \date 2016/04/12 14:31
  4 *
  5 * \author koangel
  6 * Contact: jackliu100@gmail.com
  7 *
  8 * \brief 针对新版本WKE的封装,使用C函数版本
  9 *
 10 * 为了区分改为SWkeWbkitEx名,与之前版本不冲突。
 11 */
 12 #include "stdafx.h"
 13 #include "SWkeWebkitEx.h"
 14 #pragma comment(lib,"imm32.lib")
 15 #pragma comment(lib,"msimg32.lib")
 16 
 17 namespace SOUI
 18 {
 19     SWkeWebkitEx::SWkeWebkitEx()
 20     {
 21         SWkeInit(); // 如果需要请此处屏蔽(有多个WEBVIEW时)
 22         m_pWebView = nullptr;
 23     }
 24 
 25 
 26     SWkeWebkitEx::~SWkeWebkitEx()
 27     {
 28         SWkeFinalize(); // 如果需要请此处屏蔽
 29     }
 30 
 31     void SWkeWebkitEx::SWkeInit()
 32     {
 33         wkeInitialize();
 34     }
 35 
 36     void SWkeWebkitEx::SWkeFinalize()
 37     {
 38         wkeFinalize();
 39     }
 40 
 41     BOOL SWkeWebkitEx::OnIdle()
 42     {
 43         m_render.render(m_pWebView);
 44         InvalidateRect(NULL);
 45         return TRUE;
 46     }
 47 
 48 
 49     int SWkeWebkitEx::OnCreate(void *)
 50     {
 51         m_pWebView = wkeCreateWebView();
 52         if (!m_pWebView) return 1;
 53 
 54         HWND hWnd=GetContainer()->GetHostHwnd();
 55 
 56         m_render.init(hWnd);
 57 
 58         wkeSetHostWindow(m_pWebView, hWnd);
 59         wkeSetTransparent(m_pWebView, false);
 60         wkeOnCreateView(m_pWebView, &SWkeWebkitEx::onCreateView, nullptr);
 61         wkeSetUserAgent(m_pWebView, "Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/41.0.2228.0 Safari/537.36");
 62         wkeLoadURLW(m_pWebView,m_strUrl);
 63         SetTimer(TM_TICKER,50);
 64         return 0;
 65     }
 66 
 67     void SWkeWebkitEx::OnDestroy()
 68     {
 69         if (m_pWebView)
 70         {
 71             wkeDestroyWebView(m_pWebView);
 72             m_pWebView = nullptr;
 73         }
 74     }
 75 
 76     void SWkeWebkitEx::OnPaint(IRenderTarget *pRT)
 77     {
 78         CRect rcClip;
 79         pRT->GetClipBox(&rcClip);
 80         CRect rcClient;
 81         GetClientRect(&rcClient);
 82         CRect rcInvalid;
 83         rcInvalid.IntersectRect(&rcClip, &rcClient);
 84         HDC hdc = pRT->GetDC();
 85         HDC hWebviewHC = (HDC)wkeGetViewDC(m_pWebView);
 86         if (GetStyle().m_byAlpha != 0xff)
 87         {
 88             BLENDFUNCTION bf = { AC_SRC_OVER,0,GetStyle().m_byAlpha,AC_SRC_ALPHA };
 89             AlphaBlend(hdc, rcInvalid.left, rcInvalid.top, rcInvalid.Width(), rcInvalid.Height(),hWebviewHC, rcInvalid.left - rcClient.left, rcInvalid.top - rcClient.top, rcInvalid.Width(), rcInvalid.Height(), bf);
 90         }
 91         else
 92         {
 93             BitBlt(hdc, rcInvalid.left, rcInvalid.top, rcInvalid.Width(), rcInvalid.Height(),hWebviewHC, rcInvalid.left - rcClient.left, rcInvalid.top - rcClient.top, SRCCOPY);
 94         }
 95         pRT->ReleaseDC(hdc);
 96     }
 97 
 98     void SWkeWebkitEx::OnSize(UINT nType, CSize size)
 99     {
100         __super::OnSize(nType,size);
101         wkeResize(m_pWebView, size.cx, size.cy);
102         m_render.resize(size.cx, size.cy);
103     }
104 
105     LRESULT SWkeWebkitEx::OnMouseEvent(UINT message, WPARAM wParam, LPARAM lParam)
106     {
107         if (message == WM_LBUTTONDOWN || message == WM_MBUTTONDOWN || message == WM_RBUTTONDOWN)
108         {
109             SetFocus();
110             SetCapture();
111         }
112         else if (message == WM_LBUTTONUP || message == WM_MBUTTONUP || message == WM_RBUTTONUP)
113         {
114             ReleaseCapture();
115         }
116 
117         CRect rcClient;
118         GetClientRect(&rcClient);
119 
120         int x = GET_X_LPARAM(lParam) - rcClient.left;
121         int y = GET_Y_LPARAM(lParam) - rcClient.top;
122 
123         unsigned int flags = 0;
124 
125         if (wParam & MK_CONTROL)
126             flags |= WKE_CONTROL;
127         if (wParam & MK_SHIFT)
128             flags |= WKE_SHIFT;
129 
130         if (wParam & MK_LBUTTON)
131             flags |= WKE_LBUTTON;
132         if (wParam & MK_MBUTTON)
133             flags |= WKE_MBUTTON;
134         if (wParam & MK_RBUTTON)
135             flags |= WKE_RBUTTON;
136 
137         bool bHandled = wkeFireMouseEvent(m_pWebView, message, x, y, flags); //m_pWebView->mouseEvent(message, x, y, flags);
138         SetMsgHandled(bHandled);
139         return 0;
140     }
141 
142     LRESULT SWkeWebkitEx::OnMouseWheel(UINT uMsg, WPARAM wParam, LPARAM lParam)
143     {
144         POINT pt;
145         pt.x = GET_X_LPARAM(lParam);
146         pt.y = GET_Y_LPARAM(lParam);
147         HWND hWnd=GetContainer()->GetHostHwnd();
148         ScreenToClient(hWnd, &pt);
149 
150         int delta = GET_WHEEL_DELTA_WPARAM(wParam);
151 
152         unsigned int flags = 0;
153 
154         if (wParam & MK_CONTROL)
155             flags |= WKE_CONTROL;
156         if (wParam & MK_SHIFT)
157             flags |= WKE_SHIFT;
158 
159         if (wParam & MK_LBUTTON)
160             flags |= WKE_LBUTTON;
161         if (wParam & MK_MBUTTON)
162             flags |= WKE_MBUTTON;
163         if (wParam & MK_RBUTTON)
164             flags |= WKE_RBUTTON;
165 
166 
167         bool bHandled = wkeFireMouseWheelEvent(m_pWebView, pt.x,pt.y,delta,flags); //m_pWebView->mouseEvent(message, x, y, flags);
168         SetMsgHandled(bHandled);
169         return 0;
170     }
171 
172     LRESULT SWkeWebkitEx::OnKeyDown(UINT uMsg, WPARAM wParam, LPARAM lParam)
173     {
174         unsigned int virtualKeyCode = wParam;
175         unsigned int flags = 0;
176         if (HIWORD(lParam) & KF_REPEAT)
177             flags |= WKE_REPEAT;
178         if (HIWORD(lParam) & KF_EXTENDED)
179             flags |= WKE_EXTENDED;
180 
181         bool handled = wkeFireKeyDownEvent(m_pWebView, virtualKeyCode, flags, false);
182         SetMsgHandled(handled);
183         return 0;
184     }
185 
186     LRESULT SWkeWebkitEx::OnKeyUp(UINT uMsg, WPARAM wParam, LPARAM lParam)
187     {
188         unsigned int virtualKeyCode = wParam;
189         unsigned int flags = 0;
190         if (HIWORD(lParam) & KF_REPEAT)
191             flags |= WKE_REPEAT;
192         if (HIWORD(lParam) & KF_EXTENDED)
193             flags |= WKE_EXTENDED;
194 
195         bool handled = wkeFireKeyUpEvent(m_pWebView, virtualKeyCode, flags, false);
196         SetMsgHandled(handled);
197         return 0;
198     }
199 
200     LRESULT SWkeWebkitEx::OnChar(UINT uMsg, WPARAM wParam, LPARAM lParam)
201     {
202         unsigned int charCode = wParam;
203         unsigned int flags = 0;
204         if (HIWORD(lParam) & KF_REPEAT)
205             flags |= WKE_REPEAT;
206         if (HIWORD(lParam) & KF_EXTENDED)
207             flags |= WKE_EXTENDED;
208 
209         bool handled = wkeFireKeyPressEvent(m_pWebView, charCode, flags, false);
210         SetMsgHandled(handled);
211         return 0;
212     }
213 
214     LRESULT SWkeWebkitEx::OnImeStartComposition(UINT uMsg, WPARAM wParam, LPARAM lParam)
215     {
216         wkeRect caret = wkeGetCaretRect(m_pWebView);
217 
218         CRect rcClient;
219         GetClientRect(&rcClient);
220 
221         CANDIDATEFORM form;
222         form.dwIndex = 0;
223         form.dwStyle = CFS_EXCLUDE;
224         form.ptCurrentPos.x = caret.x + rcClient.left;
225         form.ptCurrentPos.y = caret.y + caret.h + rcClient.top;
226         form.rcArea.top = caret.y + rcClient.top;
227         form.rcArea.bottom = caret.y + caret.h + rcClient.top;
228         form.rcArea.left = caret.x + rcClient.left;
229         form.rcArea.right = caret.x + caret.w + rcClient.left;
230         COMPOSITIONFORM compForm;
231         compForm.ptCurrentPos = form.ptCurrentPos;
232         compForm.rcArea = form.rcArea;
233         compForm.dwStyle = CFS_POINT;
234 
235         HWND hWnd = GetContainer()->GetHostHwnd();
236         HIMC hIMC = ImmGetContext(hWnd);
237         ImmSetCandidateWindow(hIMC, &form);
238         ImmSetCompositionWindow(hIMC, &compForm);
239         ImmReleaseContext(hWnd, hIMC);
240 
241         return 0;
242     }
243 
244     void SWkeWebkitEx::OnSetFocus()
245     {
246         wkeSetFocus(m_pWebView);
247     }
248 
249     void SWkeWebkitEx::OnKillFocus()
250     {
251         wkeKillFocus(m_pWebView);
252     }
253 
254     void SWkeWebkitEx::OnTimer(char cTimerID)
255     {
256         if (cTimerID == TM_TICKER)
257         {
258             m_render.render(m_pWebView);
259             InvalidateRect(NULL);
260         }
261     }
262 
263     BOOL SWkeWebkitEx::OnSetCursor(const CPoint &pt)
264     {
265         return TRUE;
266     }
267 
268     BOOL SWkeWebkitEx::OnAttrUrl(SStringW strValue, BOOL bLoading)
269     {
270         m_strUrl = strValue;
271         if (!bLoading)
272             wkeLoadURLW(m_pWebView,m_strUrl);
273         return !bLoading;
274     }
275 
276     wkeWebView SWkeWebkitEx::onCreateView(wkeWebView webView, void* param, const wkeNewViewInfo* info)
277     {
278         const wchar_t* target = wkeGetStringW(info->target);
279         const wchar_t* url = wkeGetStringW(info->url);
280 
281         if (wcscmp(target, L"") == 0 || wcscmp(target, L"_blank") == 0)
282         {
283             if (wcsnicmp(url, L"file:///", 8) == 0)
284                 url += 8;
285             // 此处弹出其他程序运行指定内容 WKE代码部分
286             ShellExecuteW(NULL, L"open", (LPWSTR)url, NULL, NULL, SW_SHOW);
287             return NULL;
288         }
289         else if (wcscmp(target, L"_self") == 0)
290         {
291             return webView;
292         }
293         else if (wcscmp(target, L"wontOpen") == 0)
294         {
295             return NULL;
296         }
297 
298         return webView;
299     }
300 
301 }

对于Alert本人暂未测试,请稍后自行测试。

编译请使用海面宝宝同学的WKE,妥妥的赞一个。

posted @ 2016-04-12 16:13  koangel  阅读(3000)  评论(1编辑  收藏  举报