April 18, 2024, 03:29:28 AM

News:

IonicWind Snippit Manager 2.xx Released!  Install it on a memory stick and take it with you!  With or without IWBasic!


ActiveX Examples

Started by Alan, January 16, 2007, 09:36:23 PM

Previous topic - Next topic

0 Members and 1 Guest are viewing this topic.

Alan

Hi,
I have looked around a little but havent seen any examples of using ActiveX Controls.
I'm particularly interested in the DHTMLEdit control. But even a general example of any ActiveX control to get started with would work.

Sorry if I overlooked anything in my search. There is a lot of ground to cover here.

Alan

Ionic Wind Support Team

Emergence already has a built in browser control that interface to the html COM interface for you.  See the 'browser_test.eba' example file.

Other than that you have to use COM to access an ActiveX control and it would be a little hard for a beginner.  Emergence doesn't have drop-in support for ActiveX controls like VB does.  Here is one example I have been working on:


$use "atl.lib"

DECLARE IMPORT,AtlAxWinInit()
DECLARE IMPORT,AtlAxGetControl(hwnd as UINT,IUnknown as POINTER),INT
DECLARE IMPORT,AtlAxGetHost(hwnd as UINT,IUnknown as POINTER),INT
DECLARE IMPORT,MultiByteToWideChar(CodePage:UINT,dwFlags:UINT,lpMultiByteStr:STRING,cchMultiByte:INT,lpWideCharStr:POINTER,cchWideChar:INT)
DECLARE IMPORT,SysAllocString(olestring as STRING),STRING
DECLARE IMPORT,SysFreeString(BSTR as STRING)
$define DISPATCH_METHOD 1
$define DISPATCH_PROPERTYGET 2
$define DISPATCH_PROPERTYPUT 4
$define DISPATCH_PROPERTYPUTREF 8
$define WM_FORWARDMSG       0x037F
TYPE MSG
    DEF hwnd as UINT
    DEF message as UINT
    DEF wParam as INT
    DEF lParam as INT
    DEF time as UINT
    DEF pt as POINT
END TYPE


TYPE VARIANT,1
    word        vt
    word    wReserved1
    word    wReserved2
    word    wReserved3
UINT item[2]
END TYPE

TYPE DISPPARAMS
POINTER rgvarg:'            // Array of arguments.
POINTER rgdispidNamedArgs:'   // Dispatch IDs of named arguments.
Uint cArgs:'            // Number of arguments.
Uint cNamedArgs:'         // Number of named arguments.
ENDTYPE

INTERFACE IDispatch
/*** IUnknown methods ***/
STDMETHOD QueryInterface(riid as POINTER, ppvObj as POINTER)
STDMETHOD AddRef()
STDMETHOD Release()

/*** IDispatch methods ***/
STDMETHOD GetTypeInfoCount(pctinfo as UINT BYREF)
STDMETHOD GetTypeInfo(iTInfo as UINT,lcid as POINTER,ppTInfo as POINTER)
STDMETHOD GetIDsOfNames(riid as POINTER,rgszNames as POINTER,cNames as UINT,lcid as POINTER,rgDispID as POINTER)
STDMETHOD Invoke(dispIdMember as UINT,riid as POINTER,lcid as POINTER,wFlags as WORD,pDispParams as POINTER,pVarResult as POINTER,pExcepInfo as POINTER,puArgErr as UINT BYREF)
ENDINTERFACE

CONST VT_EMPTY = 0
CONST VT_NULL = 1
CONST VT_I2 = 2
CONST VT_I4 = 3
CONST VT_R4 = 4
CONST VT_R8 = 5
CONST VT_CY = 6
CONST VT_DATE = 7
CONST VT_BSTR = 8
CONST VT_DISPATCH = 9
CONST VT_ERROR = 10
CONST VT_BOOL = 11
CONST VT_VARIANT = 12
CONST VT_UNKNOWN = 13
CONST VT_DECIMAL = 14
CONST VT_I1 = 16
CONST VT_UI1 = 17
CONST VT_UI2 = 18
CONST VT_UI4 = 19
CONST VT_I8 = 20
CONST VT_UI8 = 21
CONST VT_INT = 22
CONST VT_UINT = 23
CONST VT_VOID = 24
CONST VT_HRESULT = 25
CONST VT_PTR = 26
CONST VT_SAFEARRAY = 27
CONST VT_CARRAY = 28
CONST VT_USERDEFINED = 29
CONST VT_LPSTR = 30
CONST VT_LPWSTR = 31
CONST VT_RECORD = 36
CONST VT_FILETIME = 64
CONST VT_BLOB = 65
CONST VT_STREAM = 66
CONST VT_STORAGE = 67
CONST VT_STREAMED_OBJECT = 68
CONST VT_STORED_OBJECT = 69
CONST VT_BLOB_OBJECT = 70
CONST VT_CF = 71
CONST VT_CLSID = 72
CONST VT_BSTR_BLOB = 0xfff
CONST VT_VECTOR = 0x1000
CONST VT_ARRAY = 0x2000
CONST VT_BYREF = 0x4000
CONST VT_RESERVED = 0x8000
CONST VT_ILLEGAL = 0xffff
CONST VT_ILLEGALMASKED = 0xfff
CONST VT_TYPEMASK = 0xfff

extern _IID_IDispatch as GUID

DIALOG d1
IDispatch iDisp
IDispatch iDispUnknown
VARIANT v
AtlAxWinInit()
CREATEDIALOG d1,0,0,300,300,@CAPTION|@SYSMENU|@BORDER|@SIZE,0,"ActiveX Test Container",&dialoghandler
'MSCAL.Calendar
CONTROLEX d1,"AtlAxWin","MediaPlayer.MediaPlayer.1",4,4,296,296,@BORDER,@EXCLIENTEDGE,20

SHOWDIALOG d1
STARTTIMER d1,200
WAITUNTIL d1=0
END

SUB dialoghandler
WINRECT rc
MSG msg
SELECT @MESSAGE
CASE @IDINITDIALOG
CENTERWINDOW d1
AtlAxGetControl(GetControlHandle(d1,20),iDispUnknown)
IF iDispUnknown->QueryInterface(_IID_IDispatch,iDisp)>=0
v = PropertyPut(iDisp,"AutoStart",1,VT_BOOL,0)
filename = FILEREQUEST "Open media file",d1,1
v = InvokeMethod(iDisp,"Open",1,VT_BSTR,filename)
v = PropertyPut(iDisp,"ShowStatusBar",1,VT_BOOL,-1)
v = PropertyPut(iDisp,"ShowGotoBar",1,VT_BOOL,-1)
ENDIF
iDispUnknown->Release()
CASE @IDSIZECHANGED
GetClientSize(d1,rc.left,rc.top,rc.right,rc.bottom)
SetSize d1,rc.left+4,rc.top+4,rc.right-4,rc.bottom-4,20
CASE @IDCLOSEWINDOW
IF iDisp <> NULL
iDisp->Release()
ENDIF
CLOSEDIALOG d1,@IDOK
CASE @IDTIMER
'only way I have found to get the tracker to update in the control
v = PropertyPut(iDisp,"EnableTracker",1,VT_BOOL,-1)
default
IF ControlExists(d1,20)
msg.message = @MESSAGE
msg.lparam = @LPARAM
msg.wparam = @WPARAM
msg.hwnd = d1.hwnd
msg.time = 0
msg.pt.x=0:msg.pt.y=0
SENDMESSAGE GetControlHandle(d1,20),WM_FORWARDMSG,0,msg
ENDIF
ENDSELECT
RETURN
ENDSUB

SUB InvokeMethod(iFace as IDispatch,name as STRING,numargs as INT,...),VARIANT
POINTER pArgs,pArgs2,pTemp,pStr:pArgs = VA_START(numargs)
UINT puArgErr:puArgErr = 0
INT dispID,x
STRING method,strTemp
POINTER pMethod:pMethod = method
MultiByteToWideChar(0,0,name,-1,method,125)
variant result
DISPPARAMS param
param.rgvarg = NULL
param.cArgs = 0
param.cNamedArgs = 0
param.rgdispidNamedArgs = NULL
SET_INTERFACE iFace,IDispatch
IF iFace->GetIDsOfNames(NULL,&pMethod,1,NULL,dispID)>=0
'create the argument list
IF numargs
pArgs2 = pArgs + (4 * numargs)
param.cArgs = numargs
param.rgvarg = NEW(VARIANT,numargs)
FOR x=0 to numargs-1
param.#<VARIANT>rgvarg[x].vt = #<WORD>pArgs
pTemp = param.#<VARIANT>rgvarg[x].item
SELECT #<WORD>pArgs & 0xFFF
CASE VT_I1
CASE& VT_UI1
#<CHAR>pTemp = #<CHAR>pArgs2
pArgs2 += 4
CASE VT_I2
CASE& VT_UI2
#<WORD>pTemp = #<WORD>pArgs2
pArgs2 += 4
CASE VT_I4
CASE& VT_UI4
CASE& VT_BOOL
CASE& VT_INT
CASE& VT_UINT
CASE& VT_HRESULT
CASE& VT_ERROR
#<INT>pTemp = #<INT>pArgs2
pArgs2 += 4
CASE VT_R4
#<FLOAT>pTemp = #<FLOAT>pArgs2
pArgs2 += 4
CASE VT_R8
CASE& VT_DATE
#<DOUBLE>pTemp = #<DOUBLE>pArgs2
pArgs2 += 8
CASE VT_I8
CASE& VT_UI8
CASE& VT_CY
#<INT64>pTemp = #<INT64>pArgs2
pArgs2 += 8
'4 byte pointers
CASE VT_DISPATCH
CASE& VT_VARIANT
CASE& VT_UNKNOWN
CASE& VT_PTR
CASE& VT_CLSID
CASE& VT_LPSTR
CASE& VT_VOID
CASE& VT_LPWSTR
CASE& VT_SAFEARRAY
CASE& VT_CARRAY
#<UINT>pTemp = #<UINT>pArgs2
pArgs2 += 4
'a special VB style string
CASE VT_BSTR
pStr = #<POINTER>pArgs2
MultiByteToWideChar(0,0,#<STRING>pStr,-1,strTemp,125)
#<POINTER>pTemp = SysAllocString(strTemp)
pArgs2 += 4
DEFAULT
#<UINT>pTemp = #<UINT>pArgs2
pArgs2 += 4
'not sure so just use default case
/*CASE VT_DECIMAL
CASE VT_USERDEFINED
CASE VT_RECORD
CASE VT_FILETIME
CASE VT_BLOB
CASE VT_STREAM
CASE VT_STORAGE
CASE VT_STREAMED_OBJECT
CASE VT_STORED_OBJECT
CASE VT_BLOB_OBJECT
CASE VT_CF*/
ENDSELECT
pArgs+=4
NEXT x
ENDIF
iFace->Invoke(dispID,NULL,NULL,DISPATCH_METHOD,param,Result,NULL,puArgErr)
IF numargs
'free any allocated BSTR's
FOR x = 0 to numargs-1
IF param.#<VARIANT>rgvarg[x].vt = VT_BSTR
pStr = param.#<VARIANT>rgvarg[x].item
SysFreeString(#<STRING>pStr)
ENDIF
NEXT x
'free the parameters
DELETE param.rgvarg
ENDIF
ENDIF
RETURN result
ENDSUB

SUB PropertyPut(iFace as IDispatch,name as STRING,numargs as INT,...),VARIANT
POINTER pArgs,pArgs2,pTemp,pStr:pArgs = VA_START(numargs)
UINT puArgErr:puArgErr = 0
INT dispID,x
STRING method,strTemp
POINTER pMethod:pMethod = method
    INT dispidNamed:dispidNamed = -3:'DISPID_PROPERTYPUT;
MultiByteToWideChar(0,0,name,-1,method,125)
variant result
DISPPARAMS param
param.rgvarg = NULL
param.cArgs = 0
param.cNamedArgs = 0
param.rgdispidNamedArgs = NULL
SET_INTERFACE iFace,IDispatch
IF iFace->GetIDsOfNames(NULL,&pMethod,1,NULL,dispID)>=0
'create the argument list
IF numargs
pArgs2 = pArgs + (4 * numargs)
param.cArgs = numargs
param.cNamedArgs = 1
param.rgvarg = NEW(VARIANT,numargs)
param.rgdispidNamedArgs = dispidNamed
FOR x=0 to numargs-1
param.#<VARIANT>rgvarg[x].vt = #<WORD>pArgs
pTemp = param.#<VARIANT>rgvarg[x].item
SELECT #<WORD>pArgs & 0xFFF
CASE VT_I1
CASE& VT_UI1
#<CHAR>pTemp = #<CHAR>pArgs2
pArgs2 += 4
CASE VT_I2
CASE& VT_UI2
#<WORD>pTemp = #<WORD>pArgs2
pArgs2 += 4
CASE VT_I4
CASE& VT_UI4
CASE& VT_BOOL
CASE& VT_INT
CASE& VT_UINT
CASE& VT_HRESULT
CASE& VT_ERROR
#<INT>pTemp = #<INT>pArgs2
pArgs2 += 4
CASE VT_R4
#<FLOAT>pTemp = #<FLOAT>pArgs2
pArgs2 += 4
CASE VT_R8
CASE& VT_DATE
#<DOUBLE>pTemp = #<DOUBLE>pArgs2
pArgs2 += 8
CASE VT_I8
CASE& VT_UI8
CASE& VT_CY
#<INT64>pTemp = #<INT64>pArgs2
pArgs2 += 8
'4 byte pointers
CASE VT_DISPATCH
CASE& VT_VARIANT
CASE& VT_UNKNOWN
CASE& VT_PTR
CASE& VT_CLSID
CASE& VT_LPSTR
CASE& VT_VOID
CASE& VT_LPWSTR
CASE& VT_SAFEARRAY
CASE& VT_CARRAY
#<UINT>pTemp = #<UINT>pArgs2
pArgs2 += 4
'a special VB style string
CASE VT_BSTR
pStr = #<POINTER>pArgs2
MultiByteToWideChar(0,0,#<STRING>pStr,-1,strTemp,125)
#<POINTER>pTemp = SysAllocString(strTemp)
pArgs2 += 4
DEFAULT
#<UINT>pTemp = #<UINT>pArgs2
pArgs2 += 4
'not sure so just use default case
/*CASE VT_DECIMAL
CASE VT_USERDEFINED
CASE VT_RECORD
CASE VT_FILETIME
CASE VT_BLOB
CASE VT_STREAM
CASE VT_STORAGE
CASE VT_STREAMED_OBJECT
CASE VT_STORED_OBJECT
CASE VT_BLOB_OBJECT
CASE VT_CF*/
ENDSELECT
pArgs+=4
NEXT x
ENDIF
iFace->Invoke(dispID,NULL,NULL,DISPATCH_PROPERTYPUT,param,Result,NULL,puArgErr)
IF numargs
'free any allocated BSTR's
FOR x = 0 to numargs-1
IF param.#<VARIANT>rgvarg[x].vt = VT_BSTR
pStr = param.#<VARIANT>rgvarg[x].item
SysFreeString(#<STRING>pStr)
ENDIF
NEXT x
'free the parameters
DELETE param.rgvarg
ENDIF
ENDIF
RETURN result
ENDSUB

/*
MSCAL.Calendar
MSCAL.Calendar.7
MSComCtl2.MonthView.2
MediaPlayer.MediaPlayer.1
MSDBGrid.DBGrid
*/


Ionic Wind Support Team

Jim Scott

Where can I get a copy of the "alt.lib" file?  Or is this a library that you purchased somewhere?
Jim Scott

Ionic Wind Support Team

Select the "Tools" menu and choose "Create import library".  Select the atl.dll file and the atl.lib import library will be created.

Simple as that.

Paul.
Ionic Wind Support Team

Alan

January 16, 2007, 10:14:30 PM #4 Last Edit: January 16, 2007, 10:21:20 PM by Alan
That was fast!

I'm not a beginner. (Only here.) ;) I have worked with this control many times before. Many CMS systems use it for editing directly on the internet from within the Internet Explorer browser. I had a program working in REALBasic that used it as a Desktop WYSIWYG HTML editor. It broke after an update to the REALBasic software. (Or after I got IE7 I'm not sure?)  This project has been in the works for about 3 years. I'm still looking for the right language to use to make it work the way I want it to.

Anyway...

Looks like I will definitely have to take a better look at Aurora!

What the heck. I'm gettin a licence.

Alan

[edit]
I'm not a fan of VB. I liked VB6 a little but then naw! Nothing aganst Microsoft but I hate .Net only use it when I absolutely have to.

Jim Scott

Yep, simple as that.  Thanks.  Worked great.
Jim Scott