How to: Access the properties of the ActiveX control in the document via HTML Document Object Model

zhaozj2021-02-08  218

How to: Access the properties of the ActiveX control in the document via HTML Document Object Model

Information about this article is applied to:

Microsoft Internet Explorer (Programming) Version 4.0, 4.01, 4.01 SP1, 4.01 SP2, 5, 5.01, 5.5, 6.0

summary

9CBS Document Center Article

Little experience with MSHTML 111222 (original)

Explain how to access the elements of the web page in the HTML document object model, content. However, sometimes developers actually need access to the properties, methods, and events of the ActiveX control in the web page. For example, you need to modify / get MediaPlayer's media source after loading, and control the playback of MediaPlayer.

More information

For the interface of the ActiveX control, we need to access the document object model. Get a variety of methods for the document interface, such as Chtmlview :: gethmldocument, iWebBrowser2 :: get_document, htmlwindow2 :: get_document, etc., see the 111222 documentation. Here I use a function getDhtmldocument to represent the function of this interface. You can implement this function yourself.

Typically, we give controls a unique ID in the document for access. First we have to find this element in the document, use the ID as a parameter.

Sample code: (Refer to the source code of MFC7.0)

// Document Modified At: Sunday, August 18, 2002 11:04:50 AM, by user: jiangsheng, from computer: kfb // Access element interface through the name

HRESULT CDHtmlDialog :: GetElement (LPCTSTR szElementId, IHTMLElement ** pphtmlElement) {return GetElementInterface (szElementId, __uuidof (IHTMLElement), (void **) pphtmlElement);} // the name of the access interface via auxiliary elements function that returns the specified type interface HRESULT CDHtmlDialog :: GetElementInterface (LPCTSTR szElementId, REFIID riid, void ** ppvObj) {HRESULT hr = E_NOINTERFACE; spdispElem CComPtr ;; * ppvObj = NULL hr = GetElement (szElementId, & spdispElem); if (spdispElem) hr = SPDISPELEM-> QueryInterface (riid, ppvobj); Return HR;} // Access the ancillary function of the element interface through the name to access the element interface of the specified ID. If PbCollection returns true, returns an IHTMLELEMENTCOLLECTION collection, indicating that the page element specified by the specified ID / name is more than one.

HRESULT CDHtmlDialog :: GetElement (LPCTSTR szElementId, IDispatch ** ppdisp, BOOL * pbCollection / * = NULL * /) {CComPtr sphtmlAll; CComPtr sphtmlColl; CComPtr spdispElem; CComVariant varName; CComVariant varIndex; HRESULT hr = S_OK; CComPtr sphtmlDoc; USES_CONVERSION; * ppdisp = NULL; if (pbCollection) * pbCollection = FALSE; hr = GetDHtmlDocument (& sphtmlDoc); if (sphtmlDoc == NULL) return hr; varName.vt = VT_BSTR; varName .bstrVal = T2BSTR (szElementId); if (varName.bstrVal!) {hr = E_OUTOFMEMORY; goto Error;} hr = sphtmlDoc-> get_all (& sphtmlAll); if (sphtmlAll == NULL) goto Error; hr = sphtmlAll-> item (Varname, Varindex, & SPDispleleM); if (spdisplelem == null) {hr = e_nointerface; goto error;} spdisplelem-> queryinterface (__ uuidof (itmlelementcollection), (void **) & SPHTM LCOLL); if (sphtmlcoll) {if (pbcollection) * pbcollection = true; #ifdef _debug else {trace (tracehtml, 0, "warning: duplicate ids or names./n"); atlassert (false);} #ENDIF} ERROR: IF (Succeeded (HR)) {* PPDISP = SPDISPELEM; if (spdisplelem) (* ppdisp) -> addRef ();} Return HR;} Then we want to access objects, methods, and events, this needs The IHTMLELEMENT interface gains an object's interface, here access // get an ActiveX control interface via IHTMLObjectElement, pay attention to the ActiveX control interface and HTML object element interface is not the same interface.

You can not directly use the control interface to access IHtmlObjectElement HRESULT CDHtmlDialog :: GetControlDispatch (LPCTSTR szId, IDispatch ** ppdisp) {HRESULT hr = S_OK; CComPtr spdispElem; hr = GetElement (szId, & spdispElem); if (spdispElem) {CComPtr sphtmlObj; hr = spdispElem.QueryInterface (& sphtmlObj); if (sphtmlObj) {spdispElem.Release (); hr = sphtmlObj-> get_object (ppdisp);}} return hr;} With Active control of the interface, the following Work is much simple, for example, if you want to access the parameter attribute of the specified name of the control, simply call the getispatch interface getIdSofNames to get the DITIDSOFNAMES, then call the Invoke method to get the property // get the control properties, through the name access VARIANT CDHtmlDialog :: GetControlProperty (LPCTSTR szId, LPCTSTR szPropName) {CComVariant varEmpty; CComPtr spdispElem; GetControlDispatch (szId, & spdispElem); if (spdispElem!) return varEmpty; DISPID dispid; USES_CONVERSION; LPOLESTR pPropName = (LPOLESTR) T2COLE (SZPropname); HRESULT HR = SPDISPELEM-> GetIDSOFNAMES (IID_NULL, & PPROPNAME, 1, LOCALE_USER_DEFAULT, & DISPID); if (SUCCEEDED (hr)) return GetControlProperty (spdispElem, dispid); return varEmpty;} // set control properties, access void CDHtmlDialog :: SetControlProperty (LPCTSTR szElementId, LPCTSTR szPropName, VARIANT * pVar) by name {CComPtr spdispElem ; GetControlDispatch (szElementId, & spdispElem); if (! spdispElem) return; DISPID dispid; USES_CONVERSION; LPOLESTR pPropName = (LPOLESTR) T2COLE (szPropName); HRESULT hr = spdispElem-> GetIDsOfNames (IID_NULL, & pPropName, 1, LOCALE_USER_DEFAULT, & dispid); IF (Succeeded (HR)) SetControlProperty (SPDispleleM, Dispid, PVAR);} // Get auxiliary function of the control property,

{; GetControlDispatch (szId, & spdispElem); return GetControlProperty (spdispElem, dispid); CComPtr spdispElem} DispID access VARIANT CDHtmlDialog :: GetControlProperty (LPCTSTR szId, DISPID dispid) // helper functions provided by control properties, accessed through DispID void CDHtmlDialog :: SetControlProperty (LPCTSTR szElementId, DISPID dispid, VARIANT * pVar) {CComPtr spdispElem; GetControlDispatch (szElementId, & spdispElem); SetControlProperty (spdispElem, dispid, pVar);} // get implemented function control property VARIANT CDHtmlDialog :: GetControlProperty (IDispatch * pdispControl, DISPID dispid) {VARIANT varRet; varRet.vt = VT_EMPTY; if (pdispControl) {DISPPARAMS dispparamsNoArgs = {NULL, NULL, 0, 0}; pdispControl-> Invoke (dispid, IID_NULL, LOCALE_USER_DEFAULT, DISPATCH_PROPERTYGET, & dispparamsNoArgs, & varRet, NULL, NULL);} return varRet;!} // achieve void function set control properties CDHtmlDialog :: SetControlProperty (IDispatch * pdispControl, DISPID dispid, VARIANT * pVar) {if (pdispControl = NULL) { Dispparams dispparams = {NULL, NULL, 1, 1}; dispparams.rgvarg = pVar; DISPID dispidPut = DISPID_PROPERTYPUT; dispparams.rgdispidNamedArgs = & dispidPut; pdispControl-> Invoke (dispid, IID_NULL, LOCALE_USER_DEFAULT, DISPATCH_PROPERTYPUT, & dispparams, NULL, NULL, NULL) }} In fact, such methods are relatively low, because each access is to call GetIDSOFNAMES, and GetIDSOFNAMES is a very slow call. To optimize program efficiency, you can cache the obtained name-> DISPID mapping, but the recommended method is to import the control into the feature of the Class Wizard (New Class-> from a type library). Engineering, the COLLDISPATCHDRIVER derived class for automatically generated by class wizards is accessed attributes and methods. This method uses DISPIDs generated in the type library to access properties, methods, and events, so the speed is much better than the front of each time.

The following is the generated ColedisPatchDriver derived class code example: cstring csomeObject :: getText () {CString Result; InvokeHelper (0x18, dispatch_propertyget, vt_bstr, (void *) & results, null; return;}

Void CsomeObject :: setText (lpctstr lpsznewvalue) {static byte parms [] = vts_bstr; invokehelper (0x18, dispatch_propertyput, vt_empty, null, parms, lpsznewvalue);}

LPDISPATCH CSomeObject :: createNode (const VARIANT & type, LPCTSTR name, LPCTSTR namespaceURI) {LPDISPATCH result; static BYTE parms [] = VTS_VARIANT VTS_BSTR VTS_BSTR; InvokeHelper (0x36, DISPATCH_METHOD, VT_DISPATCH, (void *) & result, parms, & type, name, Namespaceuri; Return Result;

Another benefit is obvious, you can throw trouble work (find Dispid and call Invoke) to the class wizard, you only need to use the class wizard to automatically generate the class.

If you have to handle the control of the control, you should refer to this article in MSDN.

Handling HTML Element Events

The method of capturing an event of an ActiveX control is the same as in the article, just that the interface you need to capture the event object should be a control interface, not an element interface. The method for obtaining the IDSPATCH interface of the control has been said.

By the way, the mistakes that are easy to commit in HTML are mixed with different types of interfaces, such as

Htmlelement * pelem = null; if (palelem-> item (name, name, (lpdispatch *) & pelem) == s_ok) ... Note, Although Microsoft's document says Ihtmlelement is derived from Idispatch (Inherits from IDispatch) But this does not mean that some ways to return iDispatch are the derived interface. The above code is to commit this error, and the returned interface is directly used as the IHTMLELEMENT interface, it may be wrong. The correct access method should be the QueryInterface interface that calls the returned iDispatch to obtain the interface pointer of the specified type. See CDHTMLDIALOG :: getElement code.

reference

To get more, click the following connection to view the article in the 9CBS document library.

Little experience with MSHTML 111222 (original)

How to: get the top IWebBrowser2 interface in the ActiveX control (translation)

Use web page input data in the dialog box (Jiangsheng original)

Click the following connection to view the article in the MSDN document library

Handling HTML Element Events (English Site)

To develop a Web-based Internet Explorer solution, visit the following site:

http://msdn.microsoft.com/workshop/entry.asp

(English site)

http://msdn.microsoft.com/ie/

(English site)

http://support.microsoft.com/highlights/iep.asp?fr=0&sd=msdn (English site)

Additional query keywords: MFC Internet Explorer mshtml htmlelement htmlelementCollection htmldocument2 htmlobjectElement

Keywords: kbActiveX kbCtrl kbIE kbIE400 kbGrpDSInet kbie500 kbDSupport kbie501 kbie550 Article type: kbhowto Technology: kbIEsearch kbAudDeveloper kbSDKIESearch kbIE500Search kbSDKIE400 kbSDKIE401 kbSDKIE401SP1 kbSDKIE401SP2 kbSDKIE500 kbSDKIE501 kbSDKIE550 kbIE550Search

Last updated: January 21, 2005

转载请注明原文地址:https://www.9cbs.com/read-1845.html

New Post(0)