PDA

View Full Version : How to Reference a COM Method



Joe Caverly
09-01-2024, 14:45
I have a number of VBScripts that are using vbRichClient RC6

I am hoping that I can convert the VBScripts using the vbRichClient RC6 to thinBasic.

Here I have converted a .VBS using the vbRichClient RC6 to .tbasicc

uses "Console"

dim rc6 as iDispatch

printl "Creating rc6.cActiveScript object"

rc6 = NewCom("rc6.cActiveScript")

if IsComObject(rc6) Then
rc6.ExecuteStatement("function Times2(theNumber):Times2=theNumber*2:end function:Product=Times2(10)")
printl rc6.Eval("Product")
rc6 = Nothing
else
printl "rc6 not created"
end if

Works as it should.

So far, so good.

Here's another .vbs that I am converting to .tbasicc

Dim rc6 'as Object

Const theDLL = "E:\Documents\vb6\DirectCOM\bin\JLCUtils.dll"
Const theClass = "clsMath"

Set rc6 = CreateObject("rc6.cRegFree")
Set CScript = New Console

Set clsMath = rc6.GetInstance(theDLL,theClass)
CScript.Echo clsMath.ppp(6.59)

Set clsMath = Nothing
Set rc6 = Nothing

Class Console
Private fso
Private stdout
Private stderr

Private Sub Class_Initialize()
Set fso = CreateObject("Scripting.FileSystemObject")
Set stdout = fso.GetStandardStream(1)
Set stderr = fso.GetStandardStream(2)
End Sub

Public Sub Echo(theArg)
stdout.WriteLine theArg
End Sub

Private Sub class_Terminate()
Set stderr = Nothing
Set stdout = Nothing
Set fso = Nothing
End Sub
End Class

This .vbs code works as it should, that is, it allows Registration-Free use of COM DLLs.

Here is my conversion to .tbasicc

Uses "Console"
Uses "Trace"

Const theDLL = "E:\Documents\vb6\DirectCOM\bin\JLCUtils.dll"
Const theClass = "clsMath"

dim rc6 as iDispatch
Dim clsMath as iDispatch

rc6 = NewCom("rc6.cRegFree")

if IsComObject(rc6) Then
clsMath = rc6.GetInstance(theDLL,theClass)
if IsComObject(clsMath) then
Printl clsMath.ppp(6.59)
clsMath = Nothing
else
printl "clsMath not created"
end if
rc6 = Nothing
else
printl "rc6 not created"
end if
...which returns...

clsMath not created

Why is clsMath not being set to a COM object?
Note that it sets rc6 to a COM object.

How do I go about getting a reference to the rc6.GetInstance method,
as I do in VBScript?

Ref: https://www.vbforums.com/showthread.php?894955-vbRichClient-(RC6)-amp-RC6-Widgets-Docs-UPDATED!
Ref: https://www.vbforums.com/showthread.php?897817-Registry-Free-Object-Instantiation-using-DirectCOM-amp-RC6
Ref: https://www.vbrichclient.com/en/Downloads.htm

Thanks from Joe

ErosOlmi
23-01-2024, 01:05
I can have a surprise in next thinBasic update.

Where can I found JLCUtils.dll file?

Joe Caverly
23-01-2024, 01:31
I can have a surprise in next thinBasic update.

Where can I found JLCUtils.dll file?

JLCUtils.dll is just a simple COM Server that I made for testing.

You can download it from: https://drive.proton.me/urls/PXEWXB9GRW#yiZ1CvJ1L2bk

Link expires January 27, 2024

Thanks Eros.

Joe

ErosOlmi
23-01-2024, 01:43
thinBasic has an undocumented NEWCOM syntax that allows creation of iDispatch class objects without the need to register you DLL into the registry.
The only problem is that you need to know the ClassId of the class you want to use.
So there is no need to create an instance of rc6.cRegFree and use it to load you unregistered DLL JLCUtils.dll

Please try the following script and let me know.


uses "Console"


Dim clsMath as iDispatch

'---Class ID for clsMath class
$CLSID_clsMath = "{41A25489-48D5-4941-B792-FF9B20D32025}"

clsMath = NEWCOM CLSID $CLSID_clsMath LIB APP_SourcePath + "JLCUtils.dll"

if IsComObject(clsMath) then
Printl clsMath.ppp(6.59)
clsMath = Nothing
else
printl "clsMath not created"
end if


printl "All done, press a key to end"
WaitKey

Joe Caverly
23-01-2024, 01:52
Oh, wow!

I copied jlcutils.dll and your script (jlcutils.tbasicc) over to my R:\ drive.

Ran e:\thinbasic\thinbasicc.exe jlcutils.tbasicc

Started up process explorer,
and verified that it was using jlcutils.dll from my R:\ drive.

Indeed it is!

Thankyou very much for that!

Makes things much easier!

Joe

ErosOlmi
23-01-2024, 02:00
Yes, you can put your COM dll in any place, just refer to its full path after LIB in:

... NEWCOM CLSID sClassId LIB sLibName

This syntax was an experiment I did many month ago but never really finished and documented.
I will do next thinBasic version

Also I will add in thinAir a TypeLibrary browser, a program I derived from a Josè Roca developer that developed it in Power Basic many ears ago.
It will help in understanding what's inside a COM DLL and get ClassIds of classes.

Joe Caverly
23-01-2024, 02:20
Also I will add in thinAir a TypeLibrary browser, a program I derived from a Josè Roca developer that developed it in Power Basic many ears ago.
It will help in understanding what's inside a COM DLL and get ClassIds of classes.

That's the one I use also;
10316

Mine is probably a bit old,
as I am using TypeLib Browser 5.0.1 from 2011

Joe

ErosOlmi
23-01-2024, 15:24
That's the one I use also;
10316

Mine is probably a bit old,
as I am using TypeLib Browser 5.0.1 from 2011

Joe

Yes, more or lees is the same.
I had source code from Josè so I was able to change some minor features like possibility to copy CLSID data in right treeview.

Joe Caverly
23-01-2024, 16:36
I can now easily use all of the RC6 classes in thinBasic.

Here's the thinBasic method of using the RC6 ActiveScript Class,
without having the need to have the RC6.dll registered in Microsoft Windows...

uses "Console"
'uses "Trace"

Dim clsActiveScript as iDispatch

'---Class ID for cActiveScript class
$CLSID_cActiveScript = "{0961ABDC-07AA-483B-ADA0-55D14A2DEDCE}"

printl APP_SourcePath + "rc6.dll"

'These .dll files need to be in the same folder
'cairo_sqlite.dll
'DirectCOM.dll
'RC6.dll
'RC6Widgets.dll
'WebView2Loader.dll

clsActiveScript = NEWCOM CLSID $CLSID_cActiveScript LIB "E:\Documents\vb6\RC6BaseDlls\rc6.dll"

if IsComObject(clsActiveScript) then
clsActiveScript.ExecuteStatement("function Times2(theNumber):Times2=theNumber*2:end function:Product=Times2(10)")
printl clsActiveScript.Eval("Product")

clsActiveScript.AddCode("function Times2(theNumber):Times2=theNumber*2:end function")
printl clsActiveScript.Eval("Times2(15)")

printl clsActiveScript.Eval("2023-1945")

clsActiveScript = Nothing
else
printl "clsActiveScript not created"
end if

printl "All done, press a key to end"
WaitKey


Here's another, using the StringBuilder Class...

uses "Console"

Dim clsStringBuilder As iDispatch

'---Class ID for cStringBuilder class
$CLSID_cStringBuilder = "{8BF37C34-25F8-4605-BEF0-5069594FAA8C}"

clsStringBuilder = NEWCOM CLSID $CLSID_cStringBuilder LIB "E:\Documents\vb6\RC6BaseDlls\rc6.dll"

if IsComObject(clsStringBuilder) then
clsStringBuilder.AddNl("One")
clsStringBuilder.AddNl("Two")
clsStringBuilder.AddNl("Three")
printl clsStringBuilder.ToString

clsStringBuilder = Nothing
else
printl "clsStringBuilder not created"
end if

printl "All done, press a key to end"
WaitKey

Joe

ErosOlmi
23-01-2024, 17:34
Great!

Happy you can have your job done in thinBasic and happy you can help me to better develop this part of thinBasic that can have a lot more to give.
Will try to improve Newcom in order to have ClassName and not only ClassId for unregistered com server loaded directly from TypeLib DLL

ErosOlmi
23-01-2024, 23:22
Hi Joe,

did you had the option to work with cWebView2 class inside RC6.DLL?

Thanks a lot
Eros

Joe Caverly
23-01-2024, 23:52
Hi Joe,

did you had the option to work with cWebView2 class inside RC6.DLL?


No, that's above what I use RC6 for.

I'm mainly a console person.

I see that you have been involved with WebView2 on the PowerBasic forum;
https://forum.powerbasic.com/forum/user-to-user-discussions/programming/822534-embedding-a-webview-on-a-form-is-there-consensus

The folks on the PowerBasic forum either do not know,
or do not find useful,
the vbRichClient.

Maybe if they did,
it would open the PowerBasic users to new possibilities.

I'm sure that José Roca could get it working.

Maybe the author of the vbRichClient could offer advice.
https://www.vbforums.com/showthread.php?889202-VB6-WebView2-Binding-(Edge-Chromium)&p=5621195&viewfull=1#post5621195

Joe

ErosOlmi
24-01-2024, 01:22
I think I've done :D


Will post an example next days. I want experiment with JavaScript and DOM object.

ErosOlmi
26-01-2024, 11:39
The only thing I do not like of RC6.dll is that it is statically dependent from cairo_sqlite.dll
Not all need all the features of RC6.DLL and cairo_sqlite.dll at the same time

Otherwise RC6.DLL is a great collection of classes but with this dependency to me it is useless.