Ever heard of RhinoInside? 🤔 Want to do all the cool stuff Rhino can do without even opening Rhino? 😍 Well, buckle up, because this post will guide you through creating a Rhino console program from scratch. 💻
📝Introduction
📌 What is RhinoInside?
According to the official McNeel website:
Rhino.Inside® is an open source project which allows Rhino and Grasshopper to run inside other 64-bit Windows applications such as Revit®, AutoCAD®, etc.
In short, Rhino.Inside lets you use Rhino’s various features without actually launching Rhino.
📌 Is RhinoInside.Revit the same as RhinoInside?
When we talk about RhinoInside, the first thing that comes to mind is RhinoInside.Revit. However, the relationship between the two is that RhinoInside.Revit is built on top of RhinoInside. The former allows you to run Rhino alongside Revit, seamlessly integrating data between the two.
📋Prerequisites
Before we dive in, make sure you have the following:
- Rhino 7
- Visual Studio (https://visualstudio.microsoft.com/)
- A 64-bit computer
RhinoInside Console Program
1️⃣ Create a New Solution
Start by creating a new project.
Search for and select Console App (.NET Framework).
Make sure to select .NET Framework 4.8!
Once created, your project should look like this:
2️⃣ Configure the Environment
This step is crucial and full of potential pitfalls 🙁. You have two options:
📌 Method 1: NuGet Package
Right-click on your project and select Manage NuGet Packages.
Search for RhinoInside and install it.
Expand the References tab and set the Copy Local property of the following dependencies to False:
- Eto
- Eto.Wpf
- GH_IO
- Grasshopper
- Rhino.UI
- RhinoCommon
- RhinoWindows
This step is super important⭐⭐. RhinoInside will look for these dependencies in your Libraries folder, so they must be removed from the bin directory of our console app.
📌 Method 2: Edit RhinoInside101.csproj
For the seasoned pros, this method is faster. Open the .csproj
file with an editor and add the RhinoInside reference:
<ItemGroup>
<PackageReference Include="Rhino.Inside">
<Version>7.0.0</Version>
</PackageReference>
</ItemGroup>
3️⃣ Load RhinoInside
First, the RhinoInside constructor must be static
, meaning it’s compiled only once.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace RhinoInside101
{
internal class Program
{
// Static constructor
static Program()
{
// Initialize RhinoInside
RhinoInside.Resolver.Initialize();
}
static void Main(string[] args)
{
}
}
}
4️⃣ Load RhinoCore
Start the Rhino core module. I’m using a using
statement here, which is great for resource management 😊.
namespace RhinoInside101
{
internal class Program
{
// Static constructor
static Program()
{
// Initialize RhinoInside
RhinoInside.Resolver.Initialize();
}
static void Main(string[] args)
{
// Initialize RhinoCore
using (new Rhino.Runtime.InProcess.RhinoCore())
{
//... You can do Rhino stuff here
}
}
}
}
5️⃣ Test Run
Press Ctrl+F5 to run the program, and you might encounter this error:
Unhandled Exception: System.TypeInitializationException: The type initializer for 'RhinoInside101.Program' threw an exception. ---> System.BadImageFormatException: Could not load file or assembly 'RhinoInside, Version=7.0.0.0, Culture=neutral, PublicKeyToken=null' or one of its dependencies. An attempt was made to load a program with an incorrect format.
at RhinoInside101.Program..cctor()
--- End of inner exception stack trace ---
at RhinoInside101.Program.Main(String[] args)
Press any key to continue . . .
This is super important ⭐. Essentially, RhinoInside only supports x64 frameworks. So, let’s change our project to output x64. Open the Configuration Manager as shown below:
Click the <New..> button and change the Platform to x64.
Press Ctrl+F5 again, and you should see no errors this time.
6️⃣ Write a Rhino Function
Finally, the fun part! 😍 Goooooooooooooooood! Let’s write a simple function to create a line between two points and check its length.
namespace RhinoInside101
{
internal class Program
{
// Static constructor
static Program()
{
// Initialize RhinoInside
RhinoInside.Resolver.Initialize();
}
static void Main(string[] args)
{
// Initialize RhinoCore
using (new Rhino.Runtime.InProcess.RhinoCore())
{
//... You can do Rhino stuff here
RhinoFunction();
}
}
// Custom function to manipulate Rhino data
static void RhinoFunction()
{
Rhino.Geometry.Point3d ptA = new Rhino.Geometry.Point3d(0, 0, 0);
Rhino.Geometry.Point3d ptB = new Rhino.Geometry.Point3d(10, 0, 0);
var crv = Rhino.Geometry.NurbsCurve.CreateFromLine(new Rhino.Geometry.Line(ptA, ptB));
Console.WriteLine(crv.GetLength());
}
}
}
✍️Conclusion
Hope this helps! Feel free to reach out if you have any questions. 💌