VB external access and multiple Rhino V3  instances
- it only works with the oldest running instance of rhino, which makes it useless. If someone solves that, VB will be wonderful to use with Rhino.
- Because VB is an external access solution. It will run much slower than vbScripts AND it will only work with the oldest running session of Rhino
- The biggest problem I've found so far is that VB programs only recognize the oldest instance of Rhino that's currently running. I'm wondering if it might be possible ...

    There is a well known issue between VB external access and Rhino v3. In the case of a multiple Rhino3 instances, VB executable invoked with the CreateObject("Rhino3.Application") inside the Rhino3 executable will run only in the first started/oldest instance of the Rhino. The goal is to have a VB executable running inside the Rhino instance from which we have been starting aVB exe. One may find the solution below similar to the ActiveX method I've mentioned for the Rhino V2. Well, it is, almost identical solution, except we'll compile our new ActiveX executable with the Thread per Object option. Until we get a proper solution we can use the procedure below as a workaround.

The idea is the same as for RhinoV2: We'll send the Rhino object from initializing/button rvb script into VB ActiveX

Start and select the ActiveX EXE type of project in the VB IDE.

o Create a new class(Rhino3class.cls) and insert following code:

'in here we are receiving Rhino object
Public Sub AXInit(RhinoObject) ' from script
Set Rhino = RhinoObject
    If IsObject(Rhino) Then
        MsgBox ("We don't have an object yet")' we do not need this but just in the case we do not get an object
    End If
End Sub
We can change the above subroutine to show particular/different form(s) we have made in VB, so it may act as COMMAND$ we are sending to a regular executables with arguments ...

o Create new module (Rhinobas.bas) and insert the following code:

Public Rhino As Object

o Create new form (Rhinofrom.frm) and insert the followingcode under the buttons i.e.
something like the picture below
 Dim cmd 
 cmd = "LINE 0,0 10,10"
 Rhino.Command cmd
Dim curve
curve = Rhino.GetObject("Pick a curve")
If Rhino.IsCurve(curve) Then
   MsgBox "Picked object is a CURVE"
   MsgBox "Picked object is NOT a CURVE"
End If

Rhino start up or/and button script

! -NoEcho -Runscript (
Dim RVBobject
Sub connectActiveX()
   Set RVBobject = CreateObject("Rhino3exe.Rhino3class")
   If IsObject(RVBobject) And IsObject(Rhino) Then  'send Rhino object to the VB ActiveX InitClass
       RVBobject.AXInit(Rhino) ' object created and exist call class in our executables
   End If
Set RVBobject = Nothing
End Sub

Therefore the above was almost identical to the things we did for Rhino version 2. All we need before we make an executable in VB
is to set Thread per Object. Project->project name properties>General->Thread per Object

To see whether your VB exe has been distributed as a COM object: Start->Run->DCOMCNFG
if it does not find your ActiveX executable on the list, just start an executable and it will automatically get registered.

misc help 1 - Code to keep our form as a TOP_MOST one (even if we click in the Rhino window)

Private Sub Form_Activate()
  Call StayOnTop(Me, True, False)
End Sub

misc help 2 - to have our form closed/minimized with Rhino main window we'll use SetParent API in the load statement
(at this point we already have the rhino object so we can start using it :)

SetParent declaration:
Public Declare Function SetParent Lib "user32" (ByVal hWndChild As Long, ByVal hWndNewParent As Long) As Long

Private Sub Form_Load()
  SetParent Form1.hwnd, Rhino.WindowHandle

All the project files and start up script can be downloaded in here Download VB2Rhino3

Have phun.