Rhino inside Python

This is probably a Python.NET issue as that is the library being used in this case for interop between CPython and .NET. I’ve found the library to be pretty finicky for some cases and this may be one of them. @eirannejad has been playing with Python.NET lately and may have a better idea of what to try.

1 Like

Any news on the subject ? Is there a way to contact support for a faster discussion ?
My company is thinking of using rhino inside for a new project and we need to certify that everything we want is possible with this tool first.

Thanks for your answers.

I’m looking into this now and will let you know if I can figure anything out.

[edit] based on a quick search of stack overflow, I found this topic

You may have to create a “dummy” variable to pass in for the last out parameter. Something like

import rhinoinside
rhinoinside.load()
import System
import Rhino

dummy_out = System.Int32(0)
...
surface, error= Rhino.Geometry.NurbsSurface.CreateNetworkSurface(top_u_curves,2,2,top_v_curves,2,2,tolerance,tolerance,tolerance,dummy_out)
1 Like

It did the trick !
Now this method call goes through and at least it returns an error code but it’s my part to solve :slight_smile:
Thanks a lot for the help

2 Likes

Hey there, I’m back for more questions ^^

  1. Is there as way to execute a grasshopper script directly from rhinoinside (or at least in a headless way) ?

See I’ve been trying to make my rhino/gh use headless to embed it within a python app, I’m in the process of transcripting my GH scenarios in python with rhino inside library but I found the process to be complicated since there is no direct equivalent in RhinoCommon to the grasshopper components that I use.

  1. The best way would be to be able to call something like execute_script with my GH script but if it is not possible, is there a place to look for operations under the hood of GH components ? For example, if I want to mimic the behaviour of the Patch geometry GH component I’d like to know which RhinoCommon method of Patch is used and with which parameters. Or maybe there is a Grasshopper inside hidden library somewhere ? ^^

Thanks for your time

Hello Thomas,

you can check out my post concering your first question:

Right now it does not work for python components, so I am currently using Rhino.Compute.

1 Like

I’ve been trying to get headless grasshopper to work from cpython using rhinoinside as well. I’ve had some success working through all of the examples I can find in jupyter notebook, but ran into the same roadblock you did, Martin. I’ve only been able to get vanilla components and the C# scripting component to work, and not the ghpython components or some of the common plugins similar to your experience. I was ambitiously hoping to be able to use it to batch process diva simulations of models among other things.

For the time being I’ll probably end up setting something directly within ironpython in a Rhino instance for now, but it would be great to continue with Rhinoinside+headless grasshopper once a way through that limitation was more clear.

1 Like

Hi,

I’m having problems trying to serialise data using Rhino.FIleIO with rhino inside python.

I have succesfully created some meshes and saved them in a 3dm file, all good there. Now I’d like to export the same meshes to an obj file.

  1. the Rhino.FileIO.FileObj.Write requires a RhinoDoc object, how to get the RhinoDoc corresponding to my data ? I managed to get one by opening the saved 3dm file containing my data but I’m guessing it’s not the optimal way…

  2. when I use the Rhino.FileIO.FileObj.Write function I get a pop up asking for mesh precision, all good there but when I accept the pop up I get an error :

    System.Reflection.TargetInvocationException: Une exception a été levée par la cible d’un appel. —> System.AccessViolationException: Tentative de lecture ou d’écriture de mémoire protégée. Cela indique souvent qu’une autre mémoire est endommagée.

   à UnsafeNativeMethods.RHC_RhinoMeshObjectsWithTransform(IntPtr pArrayConstCRhinoObject, Int32& uiStyle, Transform& xform, IntPtr pMeshParameters, IntPtr pArrayMeshes, IntPtr pArrayAttributes)
   à Rhino.DocObjects.RhinoObject.MeshObjects(IEnumerable`1 rhinoObjects, MeshingParameters& parameters, Int32& uiStyle, Transform xform, Mesh[]& meshes, ObjectAttributes[]& attributes)
   à Rhino.FileIO.FileObjWriter.GetMeshObjects(FileObjWriteOptions options, List`1 rhinoObjects, MeshingParameters& parameters, Int32& uiStyle, Transform xform, Mesh[]& meshes, ObjectAttributes[]& attributes)
   à Rhino.FileIO.FileObjWriter.WriteMeshesToFile(List`1 rhinoObjects, FileObjWriteOptions options)
   à Rhino.FileIO.FileObjWriter.WriteFile(StreamWriter file, RhinoDoc doc, FileObjWriteOptions options)

Could someone enlighten me about this kind of error ? I tried giving admin rights to my python editor but it is not sufficient… Is this problem coming from export obj functions within rhinoinside ?

Also 3) Can you confirm that there is no way to get a 3D preview of the data directly from rhinoinside ?

Thanks for your help,

If you have a script I can run to repeat this, I can run it in a debugger to try and figure out what is happening

Hello Steve,

Thanks for your time, here is my code sample zipped with the virtual env used and the read 3dm file.
Here I only test opening a doc from the 3dm file and trying to export it in obj.
I don’t know why it fails and I don’t know how to get the doc from a 3dmfile python object instead of having to write it and opening it.test-export_obj.rar (8.1 MB)
Of course to be able to run it you need to change the paths at the top of the python file.

Why are you trying to run rhinoinside inside Rhino? It is intended to be used outside of Rhino.

On your command-line of your first screenshot run python, then execute the four lines you have in the second screenshot.

Nathan is correct. What is it that you are trying to do?

Thanks Nathan, my question is really stupid, I now know that Rhinocommon is called in python.

Has this idea been put out on the FreeCAD forum? @ffribeiro ?

Hi Steve, this development sounds thrilling. Are there any updates?

We are still trying to figure out some issues with Grasshopper running in a headless CPython environment.

I haven’t really tried anything specific to running GH under CPython, but we do have GH running headless in other environments. Rhino compute is a case where GH is running headless in a C# based environment.

1 Like

This new capability is very exciting!

As a suggestion, I have seen another program use a COM object/server to expose their API to Python and many other programming languages. Python is able to connect to a running instance of this program by finding an object with a specific type in the system Running Object Table (using python module comtypes), or by creating a new instance with a specific registered COM type which is then used to load the API and then start a headed instance of the program (also using comtypes).

Not sure if that makes sense, as this is not my area of expertise, but maybe it is a workable technique for Rhino/GH as well.

Hi all,

Rhino inside Python is looking very cool!
We’ve been trying to automate some Rhino workflows but have run into some issues, hopefully this is the right place to post these.

The first issue is that our python code seems to randomly quit the process sometimes.
Using the debugger gives this result right before stopping the process:

Server[pid=13780] disconnected unexpectedly

And sometimes:

[WinError 10054] An existing connection was forcibly closed by the remote host

Other than this we do not have a real traceback for this error but it does happen quite often.

The second issue does have a traceback:

2021-02-24 09:18:39.218763: Unhandled Exception: System.AccessViolationException: Attempted to read or write protected memory. This is often an indication that other memory is corrupt.
2021-02-24 09:18:40.850448: at UnsafeNativeMethods.CRhinoDoc_Delete(UInt32 serialNumber)
2021-02-24 09:18:41.933765: at Rhino.RhinoDoc.Finalize()
2021-02-24 09:18:43.065226: Execution failed

Any ideas to fix either (or both :smiley: ) of these issues?

Thanks!

1 Like

Do you have any sample scripts that demonstrate these errors?

Update
I fixed it using the GetUserText method from RhinoScriptSyntax.
Which makes me wonder :thinking:, could this RhinoScript module just not be part of RhinoInside python package? It seems like a large collection of helper functions that would really benefit python developers.

Hi all :vulcan_salute:

I am trying to collect user data from objects by importing a .3dm file in a headless doc, but with no luck thus far. There don’t seem to be any items in the archivable dictionaries :face_with_raised_eyebrow: See sample code and file below.

In this post, it is recommended to use rhinoscriptsyntax.

  • Am I doing something wrong?
  • Can rhinoscriptsyntax be used in combination with Rhino inside Python?

Thanks :raised_hands:

import rhinoinside
rhinoinside.load()
import Rhino
import pathlib

path = pathlib.Path(__file__).parent.absolute()

input_file = f"{path}\Line-With-User-Data.3dm"

rhino_doc = Rhino.RhinoDoc.CreateHeadless(None) 
rhino_doc.Import(input_file)  
rhino_objs = rhino_doc.Objects

for rhino_obj in rhino_objs:
    # get data by user dictionary
    archivable_dictionary = rhino_obj.Attributes.UserDictionary 
    archivable_dictionary_count = archivable_dictionary.Count #returns 0

    # get data by user data
    user_data_list = rhino_obj.Attributes.UserData 
    user_data_list_count = user_data_list.Count #returns 2
    archivable_dictionary2 = user_data_list.get_Item(0).Dictionary #returns archivable dictionary
    archivable_dictionary2_count = archivable_dictionary2.Count #returns 0

rhino_doc.Dispose()

Line-With-User-Data.3dm (53.1 KB)