none
VB.Net - CreateObject - Implement & get return value

    Question

  • Hi

    Within my Inventor project, there are some hap hazard methods of connection to the application.

    • Imports Inventor allows me to connect direct to the application and use all of the functions within the application
    • Imports InventorApprentice allows to access to some features without connection directly to Inventor.

    What we cant do is have both running in the same application instance. Autodesk Inventor Addins are Class projects that are loaded as the application starts which means the Class Addin is the first instance. To use Apprentice, we have to use a different method which is to create a .exe / ActiveX control that is not a Class project. This way, it can make its own independent connection. That's good but, getting the ActiveX loaded seems to be an issue. Here is what I am doing (assuming that the Apprentice connection is all set up and I just to run the ActiveX to pass data and get a return value

    Dim sIDWDocPathName As String = "C:\Temp\MyDrawing.IDW" 
     
    Dim GetDrawingView As Object = CreateObject("ApprenticeClient.GetVC") 
     
    ' and open the Assembly document
    GetDrawingView.ProcessView(sIDWDocPathName) 

    ApprenticeClient is the name of my ActiveX exe file
    GetVC is the name of the public Class inside the EXE
    ProcessView is the name of the Function I need to call within the ActiveX
    1. The above method is suggested by Autodesk but I cannot get it to work. I get an error

    So my questions are:

    Am I constructing this correctly?

    Is there an alternative method that does work?

    If I do get it to work, how would get a return value from the ActiveX? Am I right to assume that I would create a Public Member in the ActiveX and populate it from the function I call then collect its value separately? Its the connection I am actually interested in achieving though

    Thanks

    Nacho


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!

    Thursday, March 09, 2017 4:50 PM

All replies

  • Have you tried posting to the Autodesk .NET forum? Few if anyone here would be familiar with Autodesk.

    https://forums.autodesk.com/t5/net/bd-p/152


    Paul ~~~~ Microsoft MVP (Visual Basic)

    Friday, March 10, 2017 2:19 AM
  • Hi

    I have posted on that site, its my usual Forum. The CreateObject is a .Net function not specifically for Inventor so I'm advised to got to .Net forum

    Cheers

    Nacho


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!

    Friday, March 10, 2017 2:30 AM
    • Imports InventorApprentice allows to access to some features without connection directly to Inventor.

    Imports won't do that.
    https://msdn.microsoft.com/en-us/library/7f38zh8x.aspx

    "Enables type names to be referenced without namespace qualification." it doesn't actually import anything.   You need to show how you have referenced the ActiveX component.

    Friday, March 10, 2017 3:20 AM
  • Hi

    The Inventor DLL InventorApprentice is already referenced in the project. Do I need to add my exe as a reference also? Here is how I am trying to create the object

    Dim sIDWDocPathName As String = "C:\Temp\MyDrawing.IDW"  

    Dim GetDrawingView As Object = CreateObject("ApprenticeClient.GetVC")   ' and open the Assembly document

    GetDrawingView.ProcessView(sIDWDocPathName)

    ApprenticeClient is the name of my ActiveX exe file
    GetVC is the name of the public Class inside the EXE

    ProcessView is the name of the Function I need to call within the ActiveX

    Am I creating the object correctly?

    Nacho



    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!

    Friday, March 10, 2017 3:35 AM
  • Hi

    I have posted on that site, its my usual Forum. The CreateObject is a .Net function not specifically for Inventor so I'm advised to got to .Net forum

    Cheers

    Nacho


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!

    CreateObject is an instruction for COM (Component Object Model) which has been around for a couple of decades. It is supported by .NET but it's for unmanaged COM and not .NET managed code libraries.

    The error message I see in your exception trace (Cannot create ActiveX component) could be caused by a number of issues:

    1) Missing or improperly registered COM component or dependent components

    2) Insufficient permissions

    3) Internal failure of the code or misuse of the Autodesk automation API

    There is nothing in the automation code that I can see which looks unusual. CreateObject is rather basic in its use, so I suspect the issue is something specific to the use of the Autodesk automation API.


    Paul ~~~~ Microsoft MVP (Visual Basic)

    Friday, March 10, 2017 3:54 AM
  • Hi

    I have temporarily removed ALL coding & referencing from the ActiveX leaving just the following code and nothing else

    Module GetTemplates
        Sub Main()
            MsgBox("Hello World")
        End Sub
    End Module

    If it double click the ActiveX exe outside of Inventor it will run and I get the messagebox. What I cant seem to get right is the creating of the object from within my Class with all Inventor references removed in the ActiveX

    Cheers


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!

    Friday, March 10, 2017 3:59 AM
  • Hi

    I have temporarily removed ALL coding & referencing from the ActiveX leaving just the following code and nothing else

    Module GetTemplates
        Sub Main()
            MsgBox("Hello World")
        End Sub
    End Module

    If it double click the ActiveX exe outside of Inventor it will run and I get the messagebox. What I cant seem to get right is the creating of the object from within my Class with all Inventor references removed in the ActiveX

    Cheers


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!


    So it sounds like this issue is internal to the ActiveX EXE wrapper. I'm assuming this was created with Classic VB (6.0)? If this is the case then it sounds like the ActiveX EXE is unable to create the Autodesk instance for some reason (if I'm understanding the function of the ActiveX EXE correctly). I'm not familiar with the Autodesk component you are using but if it's an ActiveX control that runs in-process then it must be 32-bit in order to load from a VB 6.0 app or component.

    Paul ~~~~ Microsoft MVP (Visual Basic)

    Friday, March 10, 2017 4:25 AM
  • Hi

    The Autodesk Inventor addin is nothing more than a standard Class project with a reference to Inventor. Other than that, its pretty much a standard Class.

    I haven't 'actually' created an ActiveX wrapper. I created a standard Windows Application project,

    added a Class called cGetVC

    added module called mGetVC

    put some Hello World msgbox code in and then tested each one individually. I can run the exe successfully by double clicking it, I just cant seem to create the object from the class. Inventor 'should' be unrelated as its just a reference to the Class

    Thanks

    Nacho


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!

    Friday, March 10, 2017 4:30 AM
  • The Inventor DLL InventorApprentice is already referenced in the project. Do I need to add my exe as a reference also?

    See: https://msdn.microsoft.com/en-us/library/ms973200.aspx

    Not sure where 'my exe' fits into the scheme of things.

    Am I creating the object correctly?

    Only the people who understand the internals of the component could answer that for you, and they are most likely to be found at the support site for that software.

    Friday, March 10, 2017 4:41 AM
  • I don't think I'm understanding what you are doing. What is the purpose of the ActiveX EXE and how did you create it?

    Paul ~~~~ Microsoft MVP (Visual Basic)

    Friday, March 10, 2017 4:43 AM
  • Hi

    OK... I'll explain again in a different way.

    Class Project (NachoProj.DLL)

    I have created a standard Class Library Project to compile as a DLL. In the Class project, I have added some code to connect to Autodesk Inventor but other than that, its a Standard Class library project

    ActiveX (GetTemplates.exe)

    I haven't actually attempted to make an ActiveX project, That is the error I get from VS. What I have done is simply created a standard Windows Application in VS. I don't want a form so I have deleted it. Then, I have created a Module called mGetVC and added a Sub called Main(). I have gone into the properties of this project and change the startup to Sub Main. In the Sub Main, I have put a simple MsgBox("Hello World"). I compiled it.

    Purpose

    As Autodesk states that I cannot have Inventor & InventorApprentice running in the same instance, I have to run InventorApprentice independently. I can do that by adding the references etc to the Windows Application I have created as this will run independently in its own instance.

    So

    My Class Project is loaded when Inventor starts. This takes the current instance of Inventor. I am attempting to run GetTemplates.exe from my Class project. Because it is an exe, it will create a NEW instance of Apprentice thus, not sharing the same Inventor Instance). Right now, my GetTemplates.exe doesn't have ANY Apprentice references. It only has a msgbox that should appear when it is invoked. I know this because if I double click the exe itself, I get the msgbox.

    In the same method that you could typically create an object like Excel using CreateObject, I need to create an instance of the GetTemplates.exe or open it exclusively using CreateObject. When I create the Object using CreateObject, I should then be able to access Public Function / Subs / Members etc. For Example, I would assume this should work:

    Dim MyObject As Object = New CreateObject("GetTemplates")
    
    Dim sFilePath As String = "C:\Temp\MyFile.iam")
    MyObject.PopulateList(sFilePath)
    
    Dim GetOccurenceCount As Integer = MyObject.CountVal
    
    MyObject.Close

    But it doesn't work. When I look at some other examples of CreateObject, I see that there is additional text in the ProgID like this:

    Dim MyObject As Object = New CreateObject("GetTemplates.mGetTemplates")

    where 'mGetTemplates' is the name of the Module but am I doing this correctly? I have tried adding the Module Name, The Function Name and no additional name all of which still do not work.

    The exe works because I can manually run it, I just cant run it from my Class Library Project. I don't think that Process.Start is what I need because I need to access functions inside the exe unless I can do that with Process.Start. I can do the above with Excel and call internal defined functions but not with my GetTemplates.exe

    I then tried this which is from an Inventor Example but it also doesn't work

    Dim _GetTemplates As Object
            Try
                Try ' Try to get an active instance of Inventor 
                    _GetTemplates = System.Runtime.InteropServices.Marshal.GetActiveObject("GetTemplates")
            Catch ex As Exception
                    Dim GetAppType As Type = System.Type.GetTypeFromProgID("GetTemplates")
                    _GetTemplates = System.Activator.CreateInstance(GetAppType)
                End Try
            Catch ex As Exception
            End Try

    I don't get an error with this method but nothing happens either.

    Cheers

    Nacho


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!


    • Edited by NachoShaw Friday, March 10, 2017 11:22 AM
    Friday, March 10, 2017 11:21 AM
  • OK, I got it. I think the reason why you are having a problem with CreateObject is that you are trying to use it to launch a Windows Forms app or Console app. In .NET there is no such thing as an ActiveX or COM EXE. You can only create an in-process ActiveX or COM DLL, not an automation server like Excel, Word, etc., which runs out-of-process with respect to the client. The ActiveX EXE project type was not carried over to .NET from Visual Basic 6.0.

    If you want to run InventorApprentice in a separate process and be able to communicate with that process, there are several methods you can use. First, you can continue to use the Windows Forms app to run InventorApprentice and use IPC (Inter-process Communication) with Named Pipes. .NET has built in Classes for Named Pipes. Second, you can use the old remoting technology. This technology is a bit dated so a WCF project might be a better option from which to run InventorApprentice.


    Paul ~~~~ Microsoft MVP (Visual Basic)

    Friday, March 10, 2017 1:51 PM
  • Hi

    Thanks for the reply. I have been looking at WCF this afternoon. Not to get too much off topic but.. I see a Web.config and references to IIS & ASP. Is this the right service for a local Class library project that doesn't require internet based access?

    I created a test WCF Application to my Class Project and it connects via LocalHost

    Thanks

    Nacho


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!

    Friday, March 10, 2017 5:20 PM
  • ok....

    It seems I can use the exe if referenced & imported.

    I added a form and I can call it and the form loads so I know that the exe is connected to the Class Library. I cant however get it working without a form. I tried-

    Adding a module

    Module mGetTemplates
      Sub Main()
        MsgBox("Hello")
        Application.Run()
      End Sub
    End Module

    but nothing happens. I have set Sub Main as the project startup

    When I tried to make an instance of it, I can only access a class, not a module. There is a Class "Class1" present. I am creating the instance like this

    Dim _GetTemplates As New GetTemplates.Class1

    if I omit the Class1, I get an error in the coding at GetTemplates

    so, As a form allow it work ok, how can get it to work the same way but without a form? How would I create the instance so that Sub Main is called which starts the  exe?

    I also tried loading the form invisibly. It flashes briefly which doesn't look right

    Cheers

    Nacho


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!

    Saturday, March 11, 2017 2:11 AM
  • I added a form and I can call it and the form loads so I know that the exe is connected to the Class Library. I cant however get it working without a form.

    A module is a shared class.  You would not normally create an instance of a shared class.
    https://msdn.microsoft.com/en-us/library/aaxss7da.aspx
    "Every module has exactly one instance and does not need to be created or assigned to a variable."

    It's not clear what you are trying to achieve by using a module, but it seems that it's the wrong way to do whatever you are trying to do.

    Are you trying to create an executable that has no user interface?

    Saturday, March 11, 2017 2:35 AM
  • I'm using a module because when I don't have a module present, I get an error in visual studio telling me that I need to have a module with a Sub Main.

    Yes. I need an executable with no UI that I can load from my Class Library for it to run some code. The Reason is, I am using a method called InventorApprentice that requires its own executible instance because it can interfere with the Inventor method if I included the code in my Class Library

    Inventor & InventorApprentice need separate instances. Inventor loads with the Class Library (which loads with the Inventor Application), InvnetorApprentice is built to load with its own instance. I don't need a form, I just need to run the executable so that I can run some code in it

    Cheers


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!

    Saturday, March 11, 2017 2:43 AM
  • Yes. I need an executable with no UI that I can load from my Class Library for it to run some code.

    That sounds a lot like a class library, although 'executable' usually implies stand-alone.

    Saturday, March 11, 2017 3:34 AM
  • the InventorApprentice requires a Process to work, it cannot be used in a Class Library which is my preferred method because I would keep the code in my main Class Library. I need the Stand-alone in order for InventorApprentice to work

    Cheers

    Nacho


    Nacho is the derivative of Nigel - True fact! I am self taught in VB.Net. 50% of the time, I am right 100% of the time!

    Saturday, March 11, 2017 3:38 AM
  • if I omit the Class1, I get an error in the coding at GetTemplates

    so, As a form allow it work ok, how can get it to work the same way but without a form? How would I create the instance so that Sub Main is called which starts the  exe?

    I also tried loading the form invisibly. It flashes briefly which doesn't look right

    Without the Form (or Console) your module code runs and then the app is done. You want to keep the Form loaded so there is a message pump for the app. One thing you could do is send it to the Windows  System Tray:

    https://www.codeproject.com/articles/75822/create-a-system-tray-application-in-vb-net


    Paul ~~~~ Microsoft MVP (Visual Basic)

    Saturday, March 11, 2017 4:36 AM
  • the InventorApprentice requires a Process to work

    An application that has no user interface is a service.  See:
    https://msdn.microsoft.com/en-us/library/zt39148a(v=vs.110).aspx

    Saturday, March 11, 2017 5:47 AM