rsistant data , as the inputs and outputs of the component should be build by the data stored in the object.
thanxs in advance
Michael
here is the code of the object....
public class Proxy { public List<string> _name_in; public List<string> _name_out; public List<SerializableType> _type_in; public List<SerializableType> _type_out; public List<GH_ParamAccess> _access_in; public string _path; public string _script; public bool _internalized; public bool _working; public Proxy(List<string> name_in, List<string> name_out, List<SerializableType> type_in, List<SerializableType> type_out, List<GH_ParamAccess> access_in, string path, string script, bool internalized) { _name_in = name_in; _name_out = name_out; _type_in = type_in; _type_out = type_out; _access_in = access_in; _path = path; _script = script; _internalized = internalized; _working = true; } public Proxy() { _name_in = new List<string>(); _name_out = new List<string>(); _type_in = new List<SerializableType>(); _type_out = new List<SerializableType>(); _access_in = new List<GH_ParamAccess>(); _path = get_path_of_plugin(); _script = ""; _internalized = false; _working = false; } public static string get_path_of_plugin() { string temp_cut; string string_path = System.Reflection.Assembly.GetExecutingAssembly().Location; string string_name = System.Reflection.Assembly.GetExecutingAssembly().GetName().Name; int temp_name_int = string_name.Length + 5; int temp_path_int = string_path.Length; temp_cut = string_path.Remove(temp_path_int - temp_name_int); return temp_cut; } public static T ObjectDeserializer<T>(string XmlInput) { System.Xml.XmlDocument XmlDoc = new System.Xml.XmlDocument(); XmlDoc.Load(new System.IO.StringReader(XmlInput)); System.Xml.Serialization.XmlSerializer ser = new System.Xml.Serialization.XmlSerializer(typeof(T)); T out_ob = (T)ser.Deserialize(new System.IO.StringReader(XmlInput)); return out_ob; } public static string ObjectSerializer<T>(T SerializedObject) { System.Xml.Serialization.XmlSerializer ser = new System.Xml.Serialization.XmlSerializer(typeof(T)); System.Text.StringBuilder builder = new System.Text.StringBuilder(); XmlWriter xmllol = XmlWriter.Create(builder); ser.Serialize(xmllol, SerializedObject); return builder.ToString(); } } public class SerializableType { private Type type; // when serializing, store as a string // [DataMember] public string TypeString { get { if (type == null) return null; return type.FullName; } set { if (value == null) type = null; else { type = Type.GetType(value); } } } public Type return_Type() { return type; } // constructors public SerializableType() { type = null; } public SerializableType(Type t) { type = t; } // allow SerializableType to implicitly be converted to and from System.Type static public implicit operator Type(SerializableType stype) { return stype.type; } static public implicit operator SerializableType(Type t) { return new SerializableType(t); } // overload the == and != operators public static bool operator ==(SerializableType a, SerializableType b) { // If both are null, or both are same instance, return true. if (System.Object.ReferenceEquals(a, b)) { return true; } // If one is null, but not both, return false. if (((object)a == null) || ((object)b == null)) { return false; } // Return true if the fields match: return a.type == b.type; } public static bool operator !=(SerializableType a, SerializableType b) { return !(a == b); } // we don't need to overload operators between SerializableType and System.Type because we already enabled them to implicitly convert public override int GetHashCode() { return type.GetHashCode(); } // overload the .Equals method public override bool Equals(System.Object obj) { // If parameter is null return false. if (obj == null) { return false; } // If parameter cannot be cast to SerializableType return false. SerializableType p = obj as SerializableType; if ((System.Object)p == null) { return false; } // Return true if the fields match: return (type == p.type); } public bool Equals(SerializableType p) { // If parameter is null return false: if ((object)p == null) { return false; } // Return true if the fields match: return (type == p.type); } } public class GH_Proxy : Grasshopper.Kernel.Types.GH_Goo<Proxy> { public override Grasshopper.Kernel.Types.IGH_Goo Duplicate() { return this; } public override bool IsValid { get { return true; } } public override string ToString() { return Proxy.ObjectSerializer<Proxy>(this.Value); } public override string TypeDescription { get { return "his is a proxy"; } } public override string TypeName { get { return "his is a proxy"; } } }…
ome work to create a ZScript macro for custom routines, but you can record those in ZBrush and then merely need to edit them into my script, inline, as bulk multiple-lines you just paste in, no problem as long as you strip the ZBrush button definition at the beginning.
ZBrush has a very high initial learning curve because of its non-standard interface. However, it has the world's most powerful quad remeshing and now mesh Booleans too. I needed a replacement for slow and especially non-robust marching cubes (Cocoon/Monolith/Dodo/Aether etc. on Grasshopper) that tended to bog down or blow up. IntraLattice was a step in a good direction but it can't merge fattened lines that merely cross each other with no breaks or that physically overlap on purpose to have many curve on in to a hub. But with $800 ZBrush 4R8, the latest version, that I can create English language ZScripts for, I suddenly have, often in the blink of an eye, or at worst a few seconds, right back into Rhino Grasshopper, a perfectly joined, airtight and smoothed mesh blending of upwards of thousands of input mesh pieces that overlap in ways Rhino will never Boolean union.
There is no complicated installation of anything since it's all done in Python.
The ZBrush program itself pops up while it works, and is then automatically backgrounded to bring you back to Grasshopper. It keeps running though, for fast iterations with no program startup time.
This is a general toolkit to expose myriad very advanced features of ZBrush into being just another Grasshopper plug-in like the rest.
It works by accepting a Grasshopper mesh and writing it to disk as an OBJ file, then incorporates ZBrush settings for a given command into a text format ZScript file, also written to disk from Python based on Grasshopper inputs, then ZBrush is told to run the script via Windows command line, and the exported OBJ output is read back from disk back into a Rhino Grasshopper mesh, in about a hundred lines of code.
Despite a change in mesh definition in Rhinocommon from version 5 to 6, I made it work on both versions.
So far this is only one command, the newly improved mesh Boolean union. It gives quad meshes, but they still look healthy when quickly triangulated in Rhino (as seen on top, above).
The ZBrush ZRemesher is utterly astounding in ability to transform any mesh into a direction following, error free quad mesh that can be converted to NURBS actually, via T-Splines smooth mode. That will be the next port to Grasshopper. I hope architects pick up on this more orderly manner of patterning surfaces than the alien slime of random point Voronoi.
Commercial software has the best code, not open source stuff, so far, so this is serious work to bring world class tools into Grasshopper where we can rapidly prototype computational strategies.
Here is a thread with several examples of ZBrush Boolean union remeshing applied to 3D trusses, compared to both IntraLattice and marching cubes:
http://www.grasshopper3d.com/forum/topics/custom-unit-cell-bug-in-intralattice-plug-in?commentId=2985220%3AComment%3A1828609
The same strategy of generating script files I used to port OpenFlipper, here, for triangle remeshing, which can now be combined with ZBrush Boolean unions of arbitrary assemblies of mesh units:
http://www.grasshopper3d.com/forum/topics/best-uniform-remesher-for-patterning-organic-suraces
UPDATE: I revamped the workflow so now components feed raw ZScript into a sequencer. Then only a single ZScript is assembled and sent to ZBrush so Python never gets ahead of ZBrush (!):
It is easy to DIY roll your own now:
…
Added by Nik Willmore at 6:48am on October 12, 2017
whole design intent, but this is what Inventor is good at. The way it packages bits of 'scripted' components into 'little models' that can be stored and re-assembled is central to MCAD working.
The Inventor model shown is almost 5 years old. We don't model like that any more, however it does offer a good idea of general MCAD modeling approaches.
iParts is useful in certain situations, it could've been useful in the above model, its usefulness is often in function of the quantity of variants/configurations.
So much is scripted in GH, maybe it should also be possible to script/define/constrain/assist the placement/gluing of the results?
...
Starting point: I think we are talking across purposes. AFAIK, the solving sequence of GH's scripted components is fixed. It won't do circular dependencies... without a fight. The inter-component dependencies not 'managed' like constraints solvers do for MCAD apps.
Components and assemblies are individual files in MCAD.
Placement of these within assemblies in MCAD is a product of matrix transforms and persistent constraints. There is no bi-directional link, the link is unidirectional (downflow only), because of the use of proxies.
Consequently, scripting the placement of components is irrelevant in GH, unless you decide that each component needs to be contained in its own separate file.
This also brings up the point that generating components and assemblies in MCAD is not as straightforward. In iParts and iAssemblies, each configuration needs to be generated as a "child" (the individual file needs to be created for each child) before those children can be used elsewhere.
You notice the dilemma, if you generate 100 parts, and then you realize you only need 20, you've created 80 extra parts which you have no need for, thus generating wasteful data that may cause file management issues later on.
GH remains in a transient world, and when you decide to bake geometry (if you need to at all), you can do that in one Rhino file, and save it as the state of the design at that given moment. Very convenient for design, though unacceptable for most non-digital manufacturing methods, which greatly limits Rhino's use for manufacturing unless you combine it with an MCAD app.
One of the reasons why the distributed file approach makes perfect sense in MCAD, is that in industry you deal with a finite set of objects. Generative tools are usually not a requirement. Most mechanical engineers, product engineers and machinists would never have any use for that.
The other thing that MCAD apps like Inventor have, is the 'structured' interface that offers up all that setting out information like the coordinate systems, work planes, parameters etc in a concise fashion in the 'history tree'. This will translate into user speed. GH's canvas is a bit more freeform. I suppose the info is all there and linked, so a bit of re-jigging is easy. Also, see how T-Flex can even embed sliders and other parameter input boxes into the model itself. Pretty handy/fast to understand, which also means more speed.
True. As long as you keep the browser pane/specification tree organized and easy to query.
:)
Would love to understand what you did by sketching.
I'll start by showing what was done years ago in the Inventor model, and then share with you what I did in GH, but in another post.
Let's use one of the beams as an example:
We can isolate this component for clarity.
Notice that I've highlighted the sectional sketch with dimensions, and the point of reference, which is in relation to the CL of the column which the beam bears on. The orientation and location of the beam is already set by underlying geometry.
Here's a perspective view of the same:
The extent of the beam was also driven by reference geometry, 2 planes offset from the beam's XY plane, driven by parameters from another underlying file which serves as a parameter container:
Reference axes and points are present for all other components, here are some of them:
It starts getting cluttered if you see the reference planes as well:
Is I mentioned earlier, over time we've found better ways to define and associate geometry, parameters, manage design change, improving the efficiency of parametric models. But this model is a fair representation of a basic modeling approach, and since an Inventor-GH comparison is like comparing apples and oranges anyways, this model can be used to understand the differences and similarities, for those interested.
I haven't even gotten to your latest post yet, I will eventually.…
Added by Santiago Diaz at 10:36am on February 26, 2011
u might already noticed.
Second great thing is that is quite fast, precise and versatile (for this kind of things); also is way OPEN (meaning you can attach and or interface it with almost anything you can imagine, meaning hardware, and other sw components, etc (like a CNC machine (additive manufacturing toys..) or any sw like C# component)) making a GREAT HUGE difference with almost any other CAD (and CAM sw i must say)
i made a simple fully functional CAM component - highly powerful ! - in a couple of days...
also tested an arduino interface (meaning control over almost any elctronic device out there)... in a matter of hours...
and saw and can easily think about lots and lots of extremely cool usages of this great tool in almost any area ...
So that's why i would suggest - and will do something about for - it (or similar tools) to be teached at first stages of education !
But power comes with responsability. and is far better exploited when your are smart ;)
I think people that uses GH will be n-times as good when they don`t forget manufacturing.
This includes teachers btw....
Interesting thing to account is that all things that GH is great at (a LOT) means reducing dramatically the time spent to model almost anything...
But usually the purpose (unless the objective is just learning or doing some kind of virtual art (both legal stuff btw...;) but guess it might not be your case now and after graduating..)) is to end up by actually building some real 3D stuff...
So what Joseph is poining is key...
If you have a good teacher.. i guess it should pay more and more attention not just at your gh skills but rather the way in which you use the power, versatility and extra time gh (and additive manufacturing tech) saves, to think about how to design the stuff focusing on the ultimately relevant stuff...
optimisation...
So..
I would say that any heat interchanger like the one involved in your thesis, has to deal with fluids.. have to account for some sort of life span (involving cheaper an ideally no maintenance needed along its life...), and of course also critical the costs of manufacturing.
so... be the best one...
use GH smartly ! ie...
account for different profile paths for oil and water.. they're different fluids meaning they have different specific heat, viscosity, blah... and so... they might not even traverse the interchanger at same flow ratio, etc.
So... maybe you want to start by reshaping the grid... (parametrically...!) so you can arbitrarily and dynamically modify and get to see interactively in your definition the areas ratio of sections so as to finaly get to set the "ideal" (meainng optimum) relative areas (sections) ratio of oil to water paths... (or whatever other fluids could be !), and the material also...
Secondly you might also consider that triangles might not be well suited for the conduit sections because are not the best shape to carry most fluids... (hoses are of circular sections...worst case are kinda rectangular with rounded corners..;) not only because the're easy to manufacture but also because they minimise (optimize) flowing energy losses AND are less prone to (ie salt or debree deposits in the interior) ). so think about rounded shapes, of if you want some regular polygons stuff but 5 or more faces...kinda circular...got it ?
I love bees by the way..
and if you happen to need more interchange area (obviously another (and probably the #1 key one) figure you should be displaying interactively in your definition ) you can always add some more extrusion length...
third... the twisting stuff is cool... (artistically ;)) but i 100% agree with Joseph is far likely to involve higer costs for manufacturing with no clear benefit on surface maximization... and most probably some other losses in added friction to the flow of fluids (meaning higher costs for pumping, etc...)...
fourth...
consider the area, (then the volume!) of the "building material"... you should optimise that too ! so this could be another one of your interactive displays...
in this case... you not only can see optimisation by reducing the amount of materials to build your interchanger...
but you can also notice that if the "building tech" involves the well and common additive manufacturing process of extrusion deposits... that surface area, and that extrusion length, meaning volume and cost of raw material, also mean TIME to manufacture... and i guess you teacher will find good for you to consider and mention that one too...
fifth...
finally (for now hehe), and globally most important in the short term :)
if the objective of yor teacher is for you just to learn GH and impress him and the rest of the world then, ok, do the twist the swirl and imagine all kind of sea star and or ondulated conduit sections (maybe some recursive forms (fractals...) like snowflakes... or any n-arms (mutant !) starfishes shapes) but make sure you first get to know and validate what it will be the objectives of your evaluator...
.. in the near end this is all about passing your thesis while learning GH while having fun.. isn't it ?
go for it and best of luck !
ps: for the mid and long term.. some day take a look at linear optimisaton if you already didn't.
i think GH is a great tool to try out some linear optimisation stuff directly linking geometry related figures (areas, volumes...) along with costs figures !...
I haven't seen anything like that yet (but since i'm only a few months old in gh, i think is likely to already be something or this stuff out there. )
If not... well you can always be the first !
(and this particular case of your thesis is a great example (few key variables) to try out "automatic optimisation")
https://en.wikipedia.org/wiki/Simplex_algorithm
that... by the way...has lots to do with spatial geometry...
…
ere I'm using a GH_ObjectWrapper type. This may not be the best way about doing this, but it does work.
localSettings of type EM_Settings is the data that gets wrapped and then added to the Parameter.
Whilst everything works fine first time around, when I re-open the GH file the persistent data is lost. I need to serialize the data in some way in order to write it to a GH file and I'm not entirely sure how to do this.... I've tried for quite a while now, looking through the forum & SDK which offer clues but no joy... so I'm admitting defeat and running here!!!
Here are some of the CS bits:
public class MyComponent : GH_Component { ......... private EM_SettingsParam myParam;
private EM_Settings localSettings;
private EM_Settings mySettings;
protected override void RegisterInputParams(GH_Component.GH_InputParamManager pm) {
... myParam = new EM_SettingsParam(); EM_Settings localSettings = new EM_Settings(); myParam.PersistentData.Append(new GH_ObjectWrapper(localSettings)); pm.AddParameter(myParam, "Settings", "Se", "MySettings", GH_ParamAccess.item); }
protected override void SolveInstance(IGH_DataAccess DA) { GH_ObjectWrapper temp = new GH_ObjectWrapper(); if (!DA.GetData(5, ref temp)){ return; } mySettings = (EM_Settings)temp.Value;
...
} } public class EM_SettingsParam : GH_PersistentParam<GH_ObjectWrapper> { public EM_SettingsParam(): base(new GH_InstanceDescription("Settings", "Settings", "Represents a collection of Settings", "Params", "Primitive")) { } ...blah singular blah plural blah exposure.hidden blah... } public class EM_Settings { public bool Preview {get; set;} // (more parameters here) public EM_Settings() { Preview = true; }
}
Any help much appreciated $:)
John.…
t. This was a reasonably effective workflow for the purposes of solving the initial problem. (in reviewing this post, it seems a bit lengthy, but hopefully it's of use to others).
Link to Illustrator Script example:https://forums.adobe.com/thread/508138
Portion I used: This applies to entire illustrator document. I am using Illustrator CC 64 bit and this worked okay. Tested a few times and it failed once, but a restart of Illustrator fixed it.
var v_selection = app.activeDocument.pathItems;SwapFillStroke(v_selection); function SwapFillStroke(objSel) { for(k = 0; k < objSel.length; k++){ var subSel = objSel[k]; var c_fill = subSel.fillColor; var c_stroke = subSel.strokeColor; subSel.fillColor = c_stroke; if(!subSel.stroked) subSel.stroked = true; subSel.strokeColor = c_fill; }} redraw();
My goal was to export colored geometry, (analysis meshes for example), from Rhino and get it into illustrator with solid fills.
If you want to know how meshes are colored in rhino...there are many explanations here on the forum, a quick search will get you more detailed information.
Short version: export your lines from rhino to illustrator and run the script listed above to make the stroke color the fill color. (in illustrator, shift+X will swap the fill and stroke colors on individual objects, but does not work on multiple objects..hence the need for the script).
Detailed Version:
In my case, I had 2 case studies I was working with.1 - wind rose meshes generated from Ladybug/honeybee2 - A mesh terrain that was colored by pre-set slope values.
NOTE: There are a few plugins to bake objects with color. I used Human tools, (Bake Geometry and JustifiedText3D).http://www.grasshopper3d.com/group/human (lots of other great stuff in there too!)
I had two types of geometry. (2 different definitions)
1- An analysis mesh, (HoneyBee/LadyBug),
2 - Lines generated from mesh faces. (mesh terrain/slope values).
Export results as a DXF, and choose "do not explode". (these were my settings)
DXF seemed to produce the most consistent results.
(you could export/save as an AI file and just open them in illustrator, but that seemed to give inconsistent results with the script).
Open DXF in Illustrator:
Apply Script in illustrator:
In the terrain example, there are only 5 colors, so selection in illustrator, by color, is very easy. In the results from honeybee/ladybug, (or any analysis process I imagine), the default colors are created with a much wider range of values. I presume the legend is then created by an average of those values within a range. My point is that, with the analysis results, selecting objects by color in Illustrator is probably not a very effective workflow.
I only tested this on my instance of rhino and Illustrator. mileage may vary.
In summation, at this point, it seems that the best way to get colored mesh faces, into illustrator, is to export the meshes, (which really ends up being the mesh face edges...curves), and bringing them into illustrator and running a quick script to swap the colors. Once that is complete, you can then select ALL the objects, and change the stroke color/weight at once.…
URBS cup surface, and boy oh boy did it ever work more uniformly than using 3D orb cutters on a 3D cup. Different sized spheres return the *same* hex grid only less and less raised up as the spheres get very large.
My first question is whether these are different in character or just in Z scaling, so if I rescale them all to the same Z thickness, after extracting only the relief structure via Boolean union and splitting...and they are only *slightly* different in character, which means mere Z re-scaling of a single moderate ball size relief is an appropriate cheat to avoid slow Boolean union re-making each relief Z scale with different sized balls.
The one on the right is a very shallow relief scaled up to the same Z thickness as the pure sphere one on the left. And really, we will be mostly scaling *down* from a thicker master surface so that will attenuate any weirdness in the curvature. Indeed, I see no difference, so it makes sense to only archive the thickest one so we can control the full range of thicknesses, all the way to nearly flat bulbs. Here is the thickest one, just before the balls lose holes between them, scaled down compared to a shallow one made with huge balls to start with:
Now we just use Rhino Flow Along Surface or the Grasshopper Jackalope plug-in Sporf to morph this flat system onto our lathe form.
With Rhino history for the Flow Along Surface step I can rescale the original in Z and wait twenty seconds to see the update:
There are sad edge artifacts that will require some strategy to retain or later delete a whole row:
Maybe add more geometry to later delete or make a solid to hold stuff together?
So vastly decreasing the cell count and changing grid direction to match your cup:
The edges came out fine on this one, happily. The isocurve count has been increased by the Flow Along Surface command:
It can't be filleted yet since the joint where the cup NURBS surface has a joint now leaves feathery edges, so I went back and duplicated the border of the flat array, offset and lofted to make a protecting surface:
But that gave crazy artifacts:
I'm just going to use symmetry to fill in the joint with good faces that are not having to be joined as two halves. I had to turn my Rhino units tolerance down from a silly 0.0001 to 0.01 units to get a good re-join, but it still won't fillet without leaving holes.
SO LET'S FILLET THE FLAT THING. Same problem but a bit faster, and actually repairable manually. Rhino 5 is buggy as hell with core commands, damn it. This is not world class behavior.
Let's try it in Rhino 6 WIP, our great hope of the future: nope, the same. I had to simply manually copy the missing pieces from where it did work, which at least is easy to do in flatland. Now I get a cup:
This can *all* be done quickly in Rhino without Grasshopper, and Rhino affords you fast cage editing of the original flat array that Grasshopper cannot yet do. You just need to use Analyze Direction to be able to swap UV directions of the source or target and flip the source surface to achieve concave vs. convex patterns.
Grasshopper doesn't even have a fillet (multiple) edges component so there's not a lot of advantage to having some super slow parametric system via Grasshopper. It's not like you'll be able to see the changes fast enough to tweak a design.…
/www.grasshopper3d.com/forum/topics/vb-vs-c-vs-python
http://www.grasshopper3d.com/forum/topics/which-programming-language-should-i-focus-on-vb-or-python
VB.Net and C#
VB.Net and C# both belong to the ".Net" family of languages, and the things you can do with them in Rhino/Grasshopper are nearly 100% equivalent. Grasshopper itself was written in a combination of VB.Net and C#. Some advantages/comments, in no particular order:
Performance - VB.Net and C# scripts tend to execute faster because they are "Just-in-time" compiled as opposed to interpreted.
Autocomplete - both VB.Net and C# have rich autocomplete functionality in their respective script editor components - significantly more so than the python editor. This can be helpful for beginners since you can "hunt" for methods and properties by just typing a "." after an object name and looking at the list of available methods/properties.
Native Component development - If you eventually want to develop GHA assemblies/plug-ins for grasshopper, as of Rhino 5 you will have to use one of these two languages. However, there are plans to introduce python-based plugins in Rhino 6. Even so, the resources around plug-in development are very rich in the C# and VB.Net environments (with c# seeming to be the more popular of the two).
"Strong Typing" - VB.net to some degree, and C# especially, are less "forgiving" languages than python - they require you to know about the data type of the objects you're operating on. This can sometimes result in more verbose code - as you explicitly convert from type to type - but it also promotes good programming practice and helps make errors more understandable.
.Net ecosystem - using a .Net language means you have access to the thousands of libraries publicly available, and the process of referencing these libraries and making use of them is comparatively straightforward relative to python. More on this in the following section.
Resources/Support - At least as of 2012, VB and C# turned up more results on this forum than python, and I think you'll find slightly more expert-level coders in those languages able to help you here.
Which one between the two? C# or VB.Net? - Personally, I greatly prefer C# - I find it to be cleaner and clearer to use. I also have some programming background in C++/Java/Processing so I found the "C family" approach to be more familiar. As David and Damian point out in some of the posts linked above, C# is more popular than either python or VB.net in the rest of the coding world. However, if you are learning without any prior programming experience you may find VB.net to be a bit easier to learn.
Python
Python is, without a doubt, a beautiful and elegant language, which is probably more than can be said for VB.Net/C#. It is very popular with beginner coders, and its syntax is more readily understandable.
Syntax - Python is beautiful to read and write. Its syntax is very clear and free of extraneous punctuation (for example the ";" line endings in c#). It has many very nice language features that make common tasks more concise, like its loop syntax, list comprehensions, list "map" and "filter."
Multiple ways to talk to Rhino/Grasshopper - Python enables two general approaches to interacting with the Rhino/Grasshopper environment: RhinoCommon and RhinoScriptSyntax. If you have prior experience with Rhinoscript, you may find RhinoScriptSyntax to be preferable - it adapts many of the methods you're familiar with to the python language, and simplifies some tasks. A word of caution though - working with Rhinoscriptsyntax can introduce a performance hit relative to RhinoCommon operations. C# and VB.net by contrast can only work with RhinoCommon.
"Goodies" - The Python environment in Grasshopper has some "special features" that the other languages lack. In particular, the "GHPythonLib" library enables the ability to call most Grasshopper components from within your code, and the ability to easily enable parallel processing to improve performance. (A word of caution though - these two features do not seem to "play well" with each other, there may be bugs causing memory leaks that result in increasingly worse performance with each execution).
Cross-Platform - Unlike C#/VB.net, Python can be used natively in Rhino for Windows and Rhino for Mac.
Direct scripting in Rhino - You can also use Python directly in the Rhino environment without the need for Grasshopper if you desire, using the Rhino Python editor.
IronPython / Ecosystem issues - one frustration / potential downside to working with Python for Rhino/GH is that though there is a vast, amazing ecosystem of external libraries for Python, getting these to install/work properly in the Rhino/GH environment can be a real pain - largely because the language is actually "IronPython," a version of python designed to work closely with the .Net ecosystem. Many popular libraries like numpy and scipy are very challenging to get working in Rhino/GH.
Scripting in other programs - Especially in the AEC industry, Python is a popular scripting language for other applications. Tools like Revit, Dynamo, Blender, and ArcGIS all offer their own Python scripting interface - so learning Python in Rhino/GH can give you a leg up in eventually scripting in these other programs.
Python's Stock is Rising - there are currently a number of efforts to improve the "status" of python within the Rhino/GH ecosystem. The python editor in Rhino 6 has a number of improvements, not least of which is the ability to "compile" add-ons for Grasshopper written in python. I'm sure Giulio can speak to other upcoming improvements.
I hope this summary helps you find the right option for you. Ultimately you can't go wrong; concepts from any of the available scripting languages will make it much easier to learn the next one. In my day to day work I use a combination of both C# and python, where appropriate, and I love them both.
I hope others will feel welcome to chime in on this FAQ and add their own thoughts about advantages/disadvantages of these various options! If you have time, read through some of the other posts linked to at the beginning - there's lots of additional great information there. …
as mine but couldn't manage to make it work.
The following script was working on the python module in Rhino, but not in Ghpython.
Note that I have imported a library, and it seems to be importing on Ghpython
--------------------------------------------------------------------------------------------------
from khepri.rhino import *
def iterate_quads(f, ptss):
return [[f(p0, p1, p2, p3)
for p0, p1, p2, p3
in zip(pts0, pts1, pts1[1:], pts0[1:])]
for pts0, pts1
in zip(ptss, ptss[1:])]
def iterate_hexagono(pts, n, v):
return iterate_quads(lambda p0, p1, p2, p3: hexagono_quad(p0, p1, p2, p3, n, v), pts)
def hexagono_quad(p0, p1, p2, p3, n, v):
def chapa(pts):
return intersection(extrusion(line(pts), 280), shape_from_ref(v.copy_ref(v.realize()._ref)))
#return extrusion(line(pts), -40)
topo = intermediate_loc(p3, p2) + vx(distance(p3, p2)/4 * n), intermediate_loc(p3, p2) - vx(distance(p3, p2)/4 * n)
base = intermediate_loc(p0, p1) + vx(distance(p0, p1)/4 * n), intermediate_loc(p0, p1) - vx(distance(p0, p1)/4 * n)
lateral_esq = intermediate_loc(p3, p0), intermediate_loc(p3, p0) + vx(distance(intermediate_loc(p3, p0),intermediate_loc(p2, p1))/4 * n)
lateral_dir = intermediate_loc(p2, p1), intermediate_loc(p2, p1) - vx(distance(intermediate_loc(p2, p1),intermediate_loc(p3, p0))/4 * n)
conex_1 = intermediate_loc(p3, p2) - vx(distance(p3, p2)/4 * n), intermediate_loc(p3, p0) + vx(distance(intermediate_loc(p3, p0),intermediate_loc(p2, p1))/4 * n)
conex_2 = intermediate_loc(p3, p0) + vx(distance(intermediate_loc(p3, p0), intermediate_loc(p2, p1))/4 * n), intermediate_loc(p0, p1) - vx(distance(p0, p1)/4 * n)
conex_3 = intermediate_loc(p0, p1) + vx(distance(p0, p1)/4 * n), intermediate_loc(p2, p1) - vx(distance(intermediate_loc(p2, p1),intermediate_loc(p3, p0))/4 * n)
conex_4 = intermediate_loc(p2, p1) - vx(distance(intermediate_loc(p2, p1),intermediate_loc(p3, p0))/4 * n), intermediate_loc(p3, p2) + vx(distance(p3, p2)/4 * n)
return chapa(topo), chapa(base), chapa(lateral_esq), chapa(lateral_dir), chapa(conex_1), chapa(conex_2), chapa(conex_3), chapa(conex_4)
s = prompt_shape("Escolha superficie")
v = prompt_shape("Escolha solido")
iterate_hexagono(map_surface_division(lambda p:p, s, 5, 15), 0.5, v)
---------------------------------------------------------------------------------------------------
I imported the geometry from another cad software, and then I would select the surface and solid to perform a pattern iteration on the surface to be constrained inside the solid as a internal structure.
The problem is that the surface comes with u, v and normals all weird from the other software so I wanted to pass it through Grasshopper so I can get more control and also perform other computations on Gh on the Ghpython output. Sorry, maybe I’m over complicating. All I want is the Gh inputs working on Ghpython.
I’ll attach the Gh definition,. Need help with the Ghpython component, the rest is just me fooling around.
When I try to run the sript in Ghpython I get:
Runtime error (MissingMemberException): 'NurbsSurface' object has no attribute 'realize'
Traceback:
line 39, in map_surface_division, "<string>"
I'm also attaching the module I've imported
Any help will be very appreciated and sorry about my english
Thanks!
…