VSCode & Grasshopper & macos & Icons

Hi All,
I’ve followed the great little blog below to setup my first component on macos with VSCode for Rhino8 by by Steve Baer and Callum Sykes

While there are a few steps missing, like *.sln file and *.csproj generation, the big issue for me is how to include local png files as the component icons. Remember this is macos and VSCode.

Could someone provide some example csharp code for this, or maybe another blog post for a complete comopnent?

Cheers!

https://developer.rhino3d.com/guides/grasshopper/your-first-component-mac/

Glad you liked it. I need to review improvements to our templates that should make setup simpler.

This is really handy feedback. The .csproj will be generated by the dotnet command and the sln is created when vscode is opened / saved. I should add this to the guide.

Yes I’d agree. In Visual Studio windows creating resources and .resx’s is trivial. In VSCode I haven’t found an obvious interface for handling resources. Of course. It can be done manually which is my least favourite word in the english language.

xml inside the .csproj to embed a resource.

  <ItemGroup>
    <EmbeddedResource Include="<icon-name>.png" />
  </ItemGroup>

C# code to get an embedded resource. It would be best to do this at start up, cache the icons and have the components look at your icon cache class to prevent unnecessary reloading.

var assembly = Assembly.GetExecutingAssembly();
var imageStream = assembly.GetManifestResourceStream("<assembly-name>.<icon-name>.png");

Bitmap bitmap = new Bitmap(imageStream);
return bitmap;
2 Likes

Thanks @CallumSykes,

That was very good of you to be so prompt in trying to help me.

My apologies. Would you be so kind as to provide a full code example for a working csharp ‘hello world’ Grasshopper component that successfully loads the Icon while working on macos and VSCode?

I’m not quite achieving the desired result when trying to follow your comments, and ChatGPT hasn’t quite clarified where I’m going wrong.

Well… Okay then, as it’s you @Sholto.

test2.zip (10.6 KB)

This solution uses Embedded Resources. I prefer .resx’s as they give some nice statically typed resource names. But they’re not convenient to do without Visual Studio on windows. I’d bet Rider handles them nicely if you really need it on mac.

1 Like

You are too kind @CallumSykes . Thank you. I see how it comes together now.

Again thank you so much not only for the working code but for such a prompt response. Much appreciated.

1 Like

Hello @CallumSykes

I have tried replicating your solution to embed the png files in the grasshopper component but I’m getting an error at runtime. It compiles but when loading Grasshopper I get the following error:

Exception has occurred: CLR/System.TypeInitializationException
An exception of type 'System.TypeInitializationException' occurred in Roofer_GH.gha but was not handled in user code: 'The type initializer for 'Roofer_GH.IconLoader' threw an exception.'
 Inner exceptions found, see $exception in variables window for more details.
 Innermost exception 	 System.ArgumentNullException : Value can not be null Arg_ParamName_Name
   at System.Drawing.Bitmap.InitializeFromStream(Stream stream)
   at Roofer_GH.IconLoader.LoadIcon(String resourceName) in /Users/filipeb/10_DEV/GraphML_IO/Roofer_GH/IconLoader.cs:line 26
   at Roofer_GH.IconLoader..cctor() in /Users/filipeb/10_DEV/GraphML_IO/Roofer_GH/IconLoader.cs:line 16

Another problem I’m having is that the *.sln file is not being generated as you mention. Could this be the issue?

For anyone arriving here with the same question the reference to the resource must include the namespace of your class, that is if you want to hardcode the access as in the example provided above.

static IconLoader()
    {
      Icon = LoadIcon("Namespace.Folder.icon.png");
    }
2 Likes