//
// DHTML駆動クラス
// DHTMLで記述された UI からクラスの機能を呼び出して実行させることができる
//
#include <windows.h>
#include <atlbase.h>
CComModule _Module;
#include <atlwin.h>
#include <atlcom.h>
#include <atlhost.h>
/**
* DHTMLの外部呼出しを受理するクラス
* クラスをまぜてつくる (CMyWindow で直接 public IDispatch)
* とおちるので分離。原因は不明
*/
class CHtmlExt : public IDispatch {
public:
//----------------------------------------------------------------------------
// IUnknown 実装
HRESULT STDMETHODCALLTYPE QueryInterface(REFIID riid,
void __RPC_FAR *__RPC_FAR *ppvObject) {
if (riid == IID_IUnknown || riid == IID_IDispatch) {
if (ppvObject == NULL)
return E_POINTER;
*ppvObject = this;
AddRef();
return S_OK;
} else {
*ppvObject = 0;
return E_NOINTERFACE;
}
}
ULONG STDMETHODCALLTYPE AddRef() {
return 1;
}
ULONG STDMETHODCALLTYPE Release() {
return 1;
}
//----------------------------------------------------------------------------
// IDispatch 実装
STDMETHOD(GetTypeInfoCount)(UINT* pctinfo) {
return E_NOTIMPL;
}
STDMETHOD(GetTypeInfo)(UINT itinfo, LCID lcid, ITypeInfo** pptinfo) {
return E_NOTIMPL;
}
enum {
NONE = 0,
SETBGCOLOR = 1,
};
/**
* メソッド名とIDの対応をとるメソッド
* regszNames にメソッド名の配列がくるので、
* rgdispid に対応する dispid を返してやる
*/
STDMETHOD(GetIDsOfNames)(REFIID riid, LPOLESTR* rgszNames, UINT cNames,
LCID lcid, DISPID* rgdispid) {
UINT i;
for (i=0; i<cNames; i++) {
if (wcscmp(rgszNames[i], OLESTR("SetBgColor")) == 0) {
rgdispid[i] = SETBGCOLOR;
} else {
rgdispid[i] = NONE;
}
}
return S_OK;
}
/**
* メソッド実行
* dispidMember でメソッドが指定される。引数は pdispparams に VARIANT の配列
* の形でわたされるのでそれを使う
*/
STDMETHOD(Invoke)(DISPID dispidMember, REFIID riid,
LCID lcid, WORD wFlags, DISPPARAMS* pdispparams, VARIANT* pvarResult,
EXCEPINFO* pexcepinfo, UINT* puArgErr) {
switch (dispidMember) {
case SETBGCOLOR:
{
// 本当はここで引数チェックが必要
// 引数が 2個 (1:Body Element, 2: 色)
CComQIPtr<IHTMLBodyElement> spBody(pdispparams->rgvarg[1].pdispVal);
if (spBody != NULL) {
spBody->put_bgColor(pdispparams->rgvarg[0]);
}
}
break;
default:
return E_NOTIMPL;
}
return S_OK;
}
};
/**
* HTMLコンポーネントを処理するウインドウクラスの実装例
* CAxWindow を使って、画面いっぱいの IEコンポーネントを作成している
*/
class CMyWindow :
public CWindowImpl<CMyWindow, CWindow>,
public CHtmlExt
{
public:
CComPtr<IWebBrowser2> browser;
private:
BEGIN_MSG_MAP(CMyWindow)
MESSAGE_HANDLER(WM_CREATE, OnCreate)
MESSAGE_HANDLER(WM_DESTROY, OnDestroy)
END_MSG_MAP()
LRESULT OnCreate(UINT, WPARAM, LPARAM, BOOL&) {
// コントロール用窓
CAxWindow wnd;
RECT rect;
// 自分のサイズと同じサイズに作成
GetClientRect(&rect);
wnd.Create(m_hWnd, rect, NULL, WS_CHILD | WS_VISIBLE | WS_BORDER, 0, 1);
LPOLESTR pstrCLSID_WebBrowser = NULL;
// コントロール作成
HRESULT hr = wnd.CreateControl(OLESTR("Shell.Explorer.2"));
if (SUCCEEDED(hr)) {
// 自分自身を external 処理用に登録
hr = wnd.SetExternalDispatch(static_cast<CHtmlExt*>(this));
}
if (SUCCEEDED(hr)) {
// インターフェース取得
hr = wnd.QueryControl(&browser);
}
return SUCCEEDED(hr) ? 0 : -1;
}
LRESULT OnDestroy(UINT, WPARAM, LPARAM, BOOL&){
if (browser) {
// インターフェースがある場合は解放しておく
browser.Release();
browser.Detach();
}
// XXX アプリケーション終了
PostQuitMessage(0);
return 0;
}
};
int APIENTRY WinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPSTR lpCmdLine,
int nCmdShow)
{
int ret;
_Module.Init(NULL, hInstance);
AtlAxWinInit();
CMyWindow wnd;
wnd.Create(NULL, CWindow::rcDefault, NULL,
WS_OVERLAPPEDWINDOW|WS_VISIBLE);
#if 0
{
CComVariant vUrl("file://c:/htmlUI.htm");
CComVariant vempty;
wnd.browser->Navigate2(&vUrl, &vempty, &vempty, &vempty, &vempty);
}
#else
{
// とりあえずドキュメント生成
CComVariant vUrl("about:blank");
CComVariant vempty;
wnd.browser->Navigate2(&vUrl, &vempty, &vempty, &vempty, &vempty);
// ドキュメントを取得して…
CComPtr<IDispatch> pDisp ;
wnd.browser->get_Document(&pDisp) ;
CComQIPtr<IHTMLDocument2> pDoc = pDisp ;
if (pDoc) {
// テキストをながしこむ
VARIANT *param;
SAFEARRAY *sfArray = NULL;
BSTR bstr = SysAllocString(OLESTR("<BODY style=/"overflow-y:hidden/" id=theBody><BUTTON οnclick='window.external.SetBgColor(theBody, /"red/");'>赤</BUTTON><BUTTON οnclick='window.external.SetBgColor(theBody, /"green/");'>緑</BUTTON></BODY>"));
sfArray = SafeArrayCreateVector(VT_VARIANT, 0, 1);
if (sfArray) {
SafeArrayAccessData(sfArray,(LPVOID*) ¶m);
param->vt = VT_BSTR;
param->bstrVal = bstr;
SafeArrayUnaccessData(sfArray);
pDoc->write(sfArray);
SafeArrayDestroy(sfArray);
}
SysFreeString(bstr);
}
}
#endif
MSG msg;
while (GetMessage(&msg, NULL, 0, 0)){
TranslateMessage(&msg);
DispatchMessage(&msg);
}
ret = msg.wParam;
_Module.Term();
return ret;
}
搜索到的,备份!!!!!