Fastest way to Serialize GeometryBase

This is not necessary a pure GH question, but maybe Grasshopper has some tricks to do that.
What I need is to convert a GeometryBase Object to a byte array - for sending over networks, (strings may be also fine).
I have a basic Serialization function (first results from Stackoverflow - using BinaryFormatter)

Now while that works, it is quite slow - 200ms for a mesh sphere with 8k verts… Deserialization on the other hand is very fast.
It seems I can’t use external libraries like protobuffer, because I cant edit the Geometrybase to add the proper tags needed for Serialization to work.

Does GH have some tricks? GH_ObjectWrapper? Or if not, is there a better way than the BinaryFormatter?

I am quite lost with this and would appreciate any help!

edit: the slow serialize code example:

private void RunScript(List<GeometryBase> x, ref object A) {
    result = new List <byte[]>();
    for(int i = 0; i < x.Count; i++) {
      result.Add(ObjectToByteArray(x[i]));
    }
    A = result;
  }

  // <Custom additional code> 
  List<byte[]> result;
  public static byte[] ObjectToByteArray(Object obj) {
    System.Runtime.Serialization.Formatters.Binary.BinaryFormatter bf = new System.Runtime.Serialization.Formatters.Binary.BinaryFormatter();
    using (var ms = new MemoryStream()) {
      bf.Serialize(ms, obj);
      return ms.ToArray();
    }
  }
1 Like

GH_Convert.CommonObjectToByteArray() and vice versa. You won’t see a difference in speed though, it also uses the ISerializable approach. But at least it’s easy to call.

1 Like

thanks! and its compressed, which is nice
Just one more question: is Serialization with external libs even possible when I cant access the GeometryBase class to add tags? In other words - should i stop searching and live with the CommonObjectToByteArray() ?

edit - side note: CommonObjectToByteArray is 3-4 times slower then ObjectToByteArray() because of the compression (times become the same when using GH_Compression.Compress(ObjectToByteArray());

edit2: actually for most real world use cases the processing time is in the low ms range - only meshes take a long time…

1 Like

It depends. All GeometryBase objects can be (de)serialized using the OpenNurbs standard (which is exposed via ISerializable) and I heavily recommend using that. However RhinoCommon offers sufficient access to certain types for you to write your own (de)serializer. Meshes are potentially one of these objects, especially if you only care about the simple stuff like vertex locations and faces and normals. However meshes can contain much more complicated data such as N-Gons, curvature data, texture coordinates, double precision vertices, and user strings, not to mention actual custom user data, which you cannot hope to serialize.

Going down this road of custom serialization will at the very least mean a lot of unnecessary work on your part, and quite possibly a bunch of annoying bugs and future compatibility issues.

1 Like

then I will stick to the BinaryFormatter, also because i need a the data (userdata, etc.)
thanks!

1 Like

Hi David,

Could you provide me with an example code in C# or VB.net on how to serialize and de-serialize 3dm files? Thanks in advance.

Hi @eissamail,

If you are trying to write and read 3dm files, then use the File3dm class. There are several samples of it’s usage in the Rhino SDK samples repository.

– Dale

2 Likes

Hi Dale,

Many thanks for your reply.

Unfortunately, the Rhino SDK samples repository is very poor in terms of C# and VB.NET examples, as I’ve seen only console application that does only project conversion. We need to see how to embed a Rhino object on C# or VB.NET Win Form application, and how to save Rhino/Grasshopper project to database from a Win Form application, not from Rhino/Grasshopper.

All examples in the Rhino SDK samples repository are for Rhino/Grasshopper’s users which are suited for users, not for software developers.

Thanks again and I appreciate your help.

For being a developer, your way in asking for help is very un-developer like… Nobody knows at which point you running into problems. Complaining, but not asking a constructive question won‘t help you at all.

1 Like

Don’t know about ‘fastest’, but you can maybe use the methods Grasshopper.Kernel.GH_Convert.CommonObjectToByteArray() and Grasshopper.Kernel.GH_Convert.ByteArrayToCommonObject(). This will use opennurbs (de)serialisation under the hood.

1 Like

Hi Tom,
I am very sorry if I been misunderstood, but I mean nothing against you as I appreciate your time, help and effort.
I am working on a WinForm application that can load a preview of Rhino 3DM files so designers can use it to preview the file before loading it into Rhino.

I searched the web, including McNeel’s web pages (including all Gits), and found no useful resource to help me with that, and I was doing this for a month with no result.

Again, I am very sorry if you misunderstood me.

Thanks.

i think you are looking in the wrong place:

RhinoCommon supports a build "flavor" that allows it to be a .NET SDK for the OpenNURBS library ([www.opennurbs.org](http://www.opennurbs.org/)). This allows you to write .NET applications that can read/write the .3dm file format and since you have access to the full source debug down to every little piece of code.

1 Like

Hi Atair,

Thanks for your reply.

I did looked at this, as this was the first link to appear in the Google search, but no examples.

Thanks again.

If this has to work as part of the standalone app, or as part of a plugin for some app which isn’t Rhino, then you’ll almost certainly need the Rhino3dmIO package. It’s the .NET version of OpenNurbs meaning it’ll work without the need for Rhino.

1 Like

Hi David,

Thanks for your reply.

I know this from the Rhino3dmIO web page. Do you know how I can load the Rhino file into (for example) a PictureBox control on WinForm?
The applications should looks like this wireframe:

image

Thanks.

Rhino3dmIO doesn’t concern itself with display as far as I know, it’ll just give the geometry classes. You’ll need to display them yourself using whatever graphics platform is available to you. GDI+, open GL, Direct X, …

1 Like

Hi David,

Many thanks for your reply.

Could you help me with some sort of source code?

When Google it, I can find only how to display 3D Studio MAX and other software files, but not Rhino.

Thanks.

Do you just want to draw a thumbnail image or do you need something more complex? 3dm files save a thumbnail image in them and I could probably help figure out a technique to extract this.

1 Like

Hi Steve,

Many thanks for your offer to help, I really appreciate it.

Yes I am looking to extract the thumbnail image, but I want the user to be able to 3D rotate the object in the file without editing it, as they must do that in Rhino.

I was thinking, since examples on how to preview 3D Studio MAX files are anywhere online, can we write a small jet converter to convert Rhino files to 3D Studio MAX files and then use DirectX to load it into the PictureBox WinForm Control?

Thanks.

To display the geometry you would need to be able to extract the RenderMeshes of the objects inside a FIle3dm object. I can’t find a method for this in the documentation though…

Do you happen to know of such a method @stevebaer?

1 Like