ou will see a list of potential matches, sorted from most relevant to least relevant:
Some components and objects support initialisation codes, which means you can assign certain values directly from the popup box. You can do this by adding an equals symbol after the name and then the value you wish to assign. For example, the [Curve Offset] component allows you to specify the offset distance via the popup box by typing =5 after the offset command:
However the popup box also supports a set of special formats that allow you to create specific objects without even typing their names. As of 0.9.0077 (which hasn't been released yet at the time of writing) you can use the following shortcuts to create special objects. In the notation below optional parts of a format will be surrounded by square brackets and hashes (#) will be used to indicate numeric values. So #,#[,#] means;
at least two numeric values separated by a comma, with an optional second comma and third number.
A complete list of special formats (not all of these are supported yet in 0.9.0076):
"∙∙∙ If the format starts with a double quote, then the entire contents (minus any other double quotes) will be placed into a Text Panel.
//∙∙∙ If the format starts with two forward slashes, then the entire contents will be placed in a Text Panel.
~∙∙∙ If the format starts with a tilde, then the entire contents will be placed in a Scribble object.
#,#[,#] If the format contains two or three numerics separated by commas, a Point parameter will be created with the specified coordinates.
+[#] If the format starts with a plus symbol followed by a numeric, then an Addition component will be created.
-[#] If the format starts with a minus symbol followed by a numeric, then a Subtraction component will be created.
*[#] If the format starts with an asterisk symbol followed by a numeric, then a Multiplication component will be created.
/[#] If the format starts with a forward slash symbol followed by a numeric, then a Division component will be created.
\[#] If the format starts with a backward slash symbol followed by a numeric, then an Integer Division component will be created.
%[#] If the format starts with a percent symbol followed by a numeric, then a Modulus component will be created.
&[∙∙∙] If the format starts with an ampersand symbol, then a Concatenation component will be created.
=[∙∙∙] If the format starts with an equals symbol, then an Equality component will be created.
<[*] If the format starts with a smaller than symbol, then a Smaller Than component will be created.
>[*] If the format starts with a larger than symbol, then a Larger Than component will be created.
[# *] Pi If the format contains the text "Pi" with an optional multiplication factor, then a Pi component will be created.
# If the format can be evaluated as a single numeric value, then a Slider will be created with the specified initial value and sensible™ lower and upper limits.
#<# If the format contains two numerics separated by a smaller than symbol, a Slider with the specified limits will be created. The initial slider value will be equal to the lower limit.
#<#<# If the format contains three numerics separated by a smaller than symbol, a Slider with the specified limits will be created. The initial slider value will be the value in the middle.
#..# If the format contains two numerics separated by two or more consecutive dots, a Slider with the specified limits will be created. The initial slider value will be equal to the lower limit.
#..#..# If the format contains three numerics separated by two or more consecutive dots, a Slider with the specified limits will be created. The initial slider value will be the value in the middle.
#/#/[#] If the format contains two or three numerics separated by forward slashes, a Calendar object will be created. The order of value is day/month/year. If year is omitted then the current year is used. Note that a second slash is required because #/# is interpreted as a number and thus results in a Slider.
#:#[:#] [am/pm] If the format contains at least two numerics separated by a colon, a Clock object is created. Seconds are optional, as are am/pm suffixes.
f([...[,...[,...]]]) [= *]If the format starts with a lower case f followed by an opening bracket, an Expression component is created. A list of comma separated arguments can be provided as inputs, and anything after the optional equals symbol becomes the expression string.
Note that decimal places will be harvested from formats that indicate sliders. I.e. the format 0..2..10 is not the same as 0..2..10.00, as the former will create an integer slider from zero to ten whereas the latter will create a floating point slider with two decimal places from zero to ten.…
Added by David Rutten at 3:24pm on February 18, 2013
Analysis Tools (LAT). Our plugin has come a long way in the last 4 years and, while the legacy version will still include some small updates and contributions, we are confident in saying that the changes will be far fewer and the plugin more stable in the following months as we switch gears into the LAT effort. I can say personally that (save for a couple of small capabilities) I have made it through my list of critical features and I will hereafter be working on making these features cross-platform, cleanly-implemented, and well-documented in the new Ladybug Analysis Tools software package. As always, you can download the new release from Food4Rhino. Make sure to remove the older version of Ladybug and Honeybee and update your scripts.
The majority of changes with this release represent “icing on the cake” after a long, multi-year effort to connect to the major open source engines and datasets. So, without further adieu, here is the list of the new capabilities added with this release:
LADYBUG
Stereographic Sky Projections - Thanks to several code contributions from Byron Mardas, all Ladybug sky visualizations now support stereographic projections! Such projections are useful for understanding the hemispherical visualizations in a 2D format and they also make it easier to overlay different sky datasets on top of one another. Check here for an example file showing the sun path overlaid with helpful/harmful parts of the sky and see here for an example file using shading masks representing strategies (like an overhang) on top of the helpful / harmful portions of the sun path.
Wind Rose Upgrades - Devang Chauhan has added several new features to the Ladybug wind rose including both visual and numerical outputs of average wind velocity and frequency for each petal of the rose. Not only does this enhance the usefulness of the rose but it also paves the way for the use of the wind rose to set up CFD simulations once Butterfly is released in the near future. The new features of the wind rose can be seen in this hydra example file.
Complete Set of Local Thermal Discomfort Models - After the last release included components to evaluate radiant asymmetry discomfort (which can be modeled using these example files: 1, 2), today’s release completes Ladybug’s suite of local discomfort models from ASHRAE and the ISO by adding components to account for discomfort from cold draft. Specifically, two draft models have been added for different types of situations. The first is an older model published by P.O. Fanger, which was developed through experiments where subjects had cold air blown on the back of their neck (the most sensitive part of the body to draft). While this is useful for understanding a worst-case scenario, it can greatly overestimate the discomfort for cases of draft at ankle level - a more common occurrence that typically results from the tendency of cold air to sink. For this situation, a second draft discomfort model has been included, which is specifically meant to forecast ankle draft discomfort. The model is currently undergoing review for integration into ASHRAE-55 and a publication outlining the derivation of this model can be found here:
Liu, S., Schiavon, S., Kabanshi, A. and Nazaroff, W. (2016), Predicted Percentage Dissatisfied with Ankle Draft. Indoor Air. Accepted Author Manuscript. doi:10.1111/ina.12364 (http://escholarship.org/uc/item/9076254n).
Special thanks is due to Shichao Liu, Toby Cheung and Stefano Schiavon for sharing the model and the results of their study with the development team. The integration of draft models completes the full integration of ASHRAE-55 and EN-15251 with Ladybug. Now, you can rest assured that, if there is a certain thermal comfort standard that you need to fulfill for a given project, you can model it with the ‘bug!
Window-Based Draft Model - With the integration of draft models, the first question that one might ask is “how should these models be applied to typical design cases?” While the (soon-to-be-released) Butterfly plugin for OpenFOAM should open up a Pandora’s box of possible situations, this release of Ladybug includes a simplified downdraft model from cold vertical surfaces, which helps model several typical cases of draft discomfort. The model has been validated across several papers:
Heiselberg, P. (1994). Draught Risk From Cold Vertical Surfaces. Building and Environment, Vol 29, No. 3, 297-301
Manz, H. and Frank, T. (2003). Analysis of Thermal Comfort near Cold Vertical Surfaces by Means of Computational Fluid Dynamics. Indoor Built Environment. 13: 233-242
It has been built into the “Ladybug_Downdraft Velocity” component and has been included in an example file illustrating discomfort from cold windows in winter. The example is intended to show when glazing ratio and window U-Values are small enough to eliminate perimeter heating - a practice that is aesthetically unpleasing, costly to maintain and wasteful in its energy use.
Operative Temperature on the Psychrometric Chart - This is a feature that should have been added a long time ago but we are finally happy to say that the Ladybug_Psychrometric Chart can draw a comfort polygon assuming that the air temperature and radiant temperature are the same value (aka. an operative temperature psychrometric chart). This operative temperature chart is the format that is needed to use the ASHRAE-55 graphical method and is generally a better representation of the range of comfort in cases where one does not intend to hold the radiant temperature constant. This operative temperature capability is now set as the default on the component but you can, of course, still bring back the older comfort polygon by simply plugging in a value for meanRadiantTemperature_.
Contour Map Visualizations - Using the same inputs as the Ladybug_Recolor Mesh component, the new Ladybug_Contour Mesh component allows you to generate contoured color graphics from the results of any analysis. Now, you to maximize the use of your high-resolution studies with contours that highlight thresholds and gradients!
Image Texture Mapping for Colored Meshes - Antonello DiNunzio has added the very useful Ladybug_Texture Maker component, which allows you to bake Ladybug colored meshes with image texture maps (as opposed to the classic method that used colored vertices). This enables the creation of transparent Ladybug meshes, making it even easier to overlay Ladybug graphics with one another and with Rhino geometry:
This component also adds the ability to render Ladybug + Honeybee meshes with other rendering programs like V-Ray and 3ds Max. So you can produce Ladybug graphics like this!
Finally, image-mapped textures are also the format required for gaming and Virtual Reality software like Unity and Augmented Reality programs like Augment. So now you can export your Ladybug meshes all of the way to the virtual world!
Rhino Sun Component - If you have ever had to set up the sun for a rendering plugin and wished that you could just take your Ladybug sun and use that, then you are in luck! Byron Mardas has contributed a component that lets you set the Rhino sun based on your EPW location data, your north direction (if different from the Y-Axis) and any time of day that you want. Not only does this make it easier to coordinate the Rhino sun with your Ladybug visualizations, but you can also use it for real time shadow previews by setting your Rhino view to “Rendered” and scrolling through a slider.
Rendered Ladybug Animations - With both the image texture mapping and the Rhino sun components released, your first thought might be “it would be great if I could use this all in a rendered animation!” Thankfully, Ladybug has added a new component to help you here. The Ladybug_Render View component works in essentially the same way as the Capture View component, allowing you to make a series of images as you animate through a slider. The major benefit here is that it works with both Rhino Render and V-Ray so that animations like this can be produced effortlessly:
Cone of Vision Added - Antonello Di Nunzio has added a component that allows you to visualize various cones of vision in order to help inform your view studies. You can fine tune parameters to include just text-readable or full peripheral vision and use the resulting view cone to constrict the results of your “Ladybug_View Analysis” studies.
Terrain WIP Components Released as the Gismo Plugin - Our friend Djordje has released a new plugin Gismo - a plugin for GIS environmental analysis. As a result the following 5 terrain components: Horizon Angles, Flow Paths, Terrain Shading Mask, Terrain Generator 2, Terrain Analysis, have been removed from Ladybug+Honeybee's WIP section and are added to Gismo.
HONEYBEE
Search, Select, and Import the Hundreds Outputs from EnergyPlus/OpenStudio - Many of the power users in our community know that EnergyPlus is capable of writing several hundred different outputs from the simulation (well beyond what the basic Honeybee result readers can import). While Honeybee has always allowed one to request these outputs by adding them to the simulationOutputs_ of the component, there has not been an official workflow for searching through all of the possible outputs or importing their specific results… until now! We have added the "Honeybee_Read Result Dictionary" component, which allows you to parse the Result Data Dictionary (or .rrd file) that EnergyPlus outputs during every run of a given model. This allows you to see all of the outputs that are available for the model and you can even search through this list to find a particular output that you are interested in. Once you find what you are looking for, simply copy the text output from the component into a panel and and plug this into simulationOutputs_. Then you can use the "Honeybee_Read EP Custom Result" component to bring your custom results into GH after rerunning the simulation. The example file of an evaporative cooling tower shows how to use the workflow to request and import in the energy removed by the tower.
OpenStudio HVAC System Sizing Results - After the full integration of HVAC in the last release, we realized that a number of people wanted to run EnergyPlus models simply to evaluate the size of the Heating/Cooling system in the model (obtained from the EnergyPlus autosize calculation that is run at the start of every simulation). Such a sizing calculation can be a great way to quantify the anticipated savings from a given strategy (like shading) on the size/cost of the building’s HVAC system. To get the results of the sizing calculation, all that one needs to do is connect the output eioFile from the OpenStudio component to the Honeybee_Read HVAC Sizing component. The outputs will indicate the peak heating/cooling loads of each zone (in Watts) as well as the size of each piece of HVAC equipment in the model. The next time that you are on a project that is about to value-engineer out an exterior shading system, use the workflow in the following example file to show that the client will probably end up paying for it with a more expensive HVAC system: Quantifying HVAC Sizing Impact of Shade.
Improved Memory Usage When Building Large Energy Models - As we take the capabilities of Honeybee to larger and larger models, many of us have begun to run up against a particular limitation of our machines: memory. After upgrading our machines to have 32 GBs of RAM, there was only one way left to alleviate the problem: restructure some of the code. Honeybee now uses an enhanced approach that ensures all the previous iterations of Honeybee objects will be removed from the memory once there is a change. In any case, the considerations of memory are definitely something that we intend to improve with the future Honeybee[+] plugin.
Workflow to Import gbXML Files - While GrizzlyBear has been around for several years, enabling us to export Honeybee zones to gbXML, we have gone for quite some time without a workflow to import gbXML files to Honeybee. The new Honeybee_gbXML to Honeybee component addresses this and establishes an easier path to import models from Revit into honeybee. You can read more about the component in this post.
Window Frame Capabilities Added to OpenStudio - After the implementation of LBNL THERM / WINDOW capabilities in the last two releases, there was one final bridge to build in the Honeybee workflow - fully connecting LBNL WINDOW to Honeybee’s OpenStudio workflow. This release of Honeybee will now write all FrameAndDivider objects exported from LBNL WINDOW glazing systems into the energy simulation, enabling you to account for the frame’s thermal bridging effects. As long as the construction is brought in with the Honeybee_Import WINDOW IDF Report component, the frames associated with the construction will be assigned to all windows that have the construction. Finally, it is worth noting that the current Honeybee will also write all glass spectral data as well as gas (or gas mixture) materials into the simulation. This means that essentially all properties of any IDF export that one makes from LBNL WINDOW can be factored into the OpenStudio energy simulation (with the only exception being BSDF materials).
OpenStudio Daylight Sensors Added - In our previous releases of Honeybee, the only means of correctly account for daylight sensors in an energy simulation was to run an annual daylight simulation and use the resulting schedules for the lighting in the energy simulation. However, this can take a lot of time and work to set up and run, particularly if the daylight control (at the end of the day) will be driven by just one sensor per room. Now, we have added another option, which uses OpenStudio/EnergyPlus’s built-in daylight controls. You can assign just a point and an illuminance target on the “Set Zone Thresholds” component and the lighting will be automatically adjusted in the course of the simulation. It should also be noted that the addition of daylight sensors has also coincided with the addition of blind/shade control based on glare. The same sensor point for daylight can be used to drive dynamic shades in the energy simulation based on glare experienced at this point. This example file shows how to set up daylight controls on the EnergyPlus model and check the lighting power results to see the effect.
Better Defaults for Natural Ventilation - After many good people wrote to me informing me that Honeybee overestimates natural ventilation airflow and I wrote back showing the way that I intended natural ventilation to be set up with the component, it dawned on me that I had selected some poor component defaults. Accordingly, this release includes a window-based natural ventilation option on the Set EP Airflow component that corrects for some of the common issues that I have seen. Insect screens are included by default and the component runs a general check to see if wind-driven cross ventilation is possible before auto-assigning it. The component will air on the side of more-conservative, lower airflow rates unless the user overrides the defaults. Finally, it’s worth noting that all of these changes have not affected the freedom of the Custom WindAndStack option on the component. The new defaults can be viewed in this example file.
CFD Results Can be Plugged into Microclimate Maps - In preparation for the (very soon) release of the Butterfly that connects to the OpenFOAM CFD platform, we just wanted to note that all of the microclimate map recipes can now take an input of a csv file with a matrix of CFD results for wind speed. For the time being, we have used these to produce very high-accuracy, high resolution maps of outdoor comfort. There will be more to follow soon!
We should also note that, in the last release I mentioned that we would be phasing out the EnergyPlus component so that all efforts are focused on the OpenStudio component. While I reiterate that all of the features of the EnergyPlus component are available in the OpenStudio component and I encourage everyone to use the OpenStudio component in order to take advantage of its HVAC capabilities, I have come to realize that many prefer to use the EnergyPlus component out of habit and have not yet gotten the time to understand why the OpenStudio component is an improvement over the EnergyPlus component. As a result, we have decided to leave the EnergyPlus component in place for the time being so that everyone has more time to understand this. The future Ladybug Analysis Tools platform will only interact with EnergyPlus through OpenStudio and so it is recommended that everyone use these two components in the Honeybee plugin will serve as an educational resource to understand our current path moving forward with OpenStudio.
Lastly, it is with great pleasure that we welcome Devang Chauhan and Byron Mardas to the developer team! As mentioned previously Devang has contributed several updates to the Ladybug Wind Rose in addition to finding and solving a multitude of bugs in other components. Byron has contributed code that has enabled the previously-mentioned stereographic sky projections along with a better method for running the Ladybug Sky Mask. Finally, Byron has contributed the Rhino Sun component, which allows you to coordinate your Rhino renders with your Ladybug data. Welcome to the Ladybug team, gentlemen!
As always let us know your comments and suggestions. Cheers!
Ladybug Analysis Tools Development Team…
n, so if you want Strings, be sure to encase them in double quotes:
Concat = " alcohol doesn't affect me"
● Added initialization code to the Cull Nth component.
● Added initialization code to the Cull Index component.
● Added initialization code to the Random Reduce component.
● Added initialization code to the Duplicate component.
● Added initialization code to the List Item component.
● Added initialization code to the Repeat Data component.
● Added initialization code to the Shift List component.
● Added initialization code to the Split List component.
● Added initialization code to the Sequence component.
● Added initialization code to the Constant E component.
● Added initialization code to the Constant Epsilon component.
● Added initialization code to the Factorial component.
● Added initialization code to the Fibonacci component.
● Added initialization code to the Golden Ratio component.
● Added initialization code to the Constant Pi component.
● Added initialization code to the Random component.
● Added initialization code to the Range component.
● Added initialization code to the Series component.
● Added initialization code to the Square component.
● Added initialization code to the Square Root component.
● Added initialization code to the Cube component.
● Added initialization code to the Cube Root component.
● Added initialization code to the Log10 component.
● Added initialization code to the Log component.
● Added initialization code to the Exponent component.
● Added initialization code to the Power of 2 component.
● Added initialization code to the Power of 10 component.
● Added initialization code to the Sine component.
● Added initialization code to the Sinc component.
● Added initialization code to the Cosine component.
● Added initialization code to the Tangent component.
● Added initialization code to the ArcSine component.
● Added initialization code to the ArcCosine component.
● Added initialization code to the ArcTangent component.
● Added initialization code to the Secant component.
● Added initialization code to the Cosecant component.
● Added initialization code to the Cotangent component.
● Added initialization code to the One over X component.
● Added initialization code to the Absolute component.
● Added initialization code to the Sign component.
● Added initialization code to the ToDegrees component.
● Added initialization code to the ToRadians component.
● Added initialization code to the N-Base log component.
● Added initialization code to the Smaller Than component.
● Added initialization code to the Larger Than component.
● Added initialization code to the Equal To component.
● Added initialization code to the Similar To component.
● Added initialization code to the Addition component.
● Added initialization code to the Subtraction component.
● Added initialization code to the Multiplication component.
● Added initialization code to the Division component.
● Added initialization code to the Integer Division component.
● Added initialization code to the Minimum component.
● Added initialization code to the Maximum component.
● Added initialization code to the Modulus component.
● Added initialization code to the Power component.
● Added initialization code to the Concatenate component.
● Added initialization code to the String Split component.
● Added initialization code to the String Join component.
● Added initialization code to the Evaluate Length component.
● Added initialization code to the Circle component.
● Added initialization code to the Circle CNR component.
● Added initialization code to the Arc component.
● Added initialization code to the Curve component.
● Added initialization code to the Interpolated Curve component.
● Added initialization code to the Offset Curve component.
● Added initialization code to the Offset Curve Loose component.
● Added initialization code to the Offset Curve On Surface component.
● Added initialization code to the Extend Curve component.
● Added initialization code to the Catenary component.
● Added initialization code to the Line SDL component.
● Added initialization code to the Fillet component.
● Added initialization code to the Fillet Distance component.
● Added initialization code to the Move component.
● Added initialization code to the Scale component.
● Added initialization code to the Mesh Plane component.
● Added initialization code to the Mesh Box component.
● Added initialization code to the Mesh Sphere component.
● Added initialization code to the Sphere component.
● Added initialization code to the Surface Offset component.
● Added initialization code to the Surface Offset Loose component.
● Added initialization code to the Divide Curve component.
● Added initialization code to the Divide Curve Length component.
● Added initialization code to the Divide Curve Distance component.
● Added initialization code to the Curve Frames component.
● Added initialization code to the Curve Perpendicular Frames component.
● Added initialization code to the Square Grid component.
● Added initialization code to the Rectangular Grid component.
● Added initialization code to the Vector Amplitude component.
--
David Rutten
david@mcneel.com
Poprad, Slovakia
…
e a fundamental failure on my part. On the other hand, Grasshopper isn't supposed to be on a par with most other 3D programs. It is emphatically not meant for manual/direct modelling. If you would normally tackle a problem by drawing geometry by hand, Grasshopper is not (and should never be advertised as) a good alternative.
I get that. That’s why that 3D shape I’m trying to apply the voronoi to was done in NX. I do wonder where the GUI metaphor GH uses comes from. It reminds me of LabVIEW.
"What in other programs is a dialog box, is 8 or 10 components strung together in grasshopper. The wisdom for this I often hear among the grasshopper community is that this allows for parametric design."
Grasshopper ships with about 1000 components (rounded to the nearest power of ten). I'm adding more all the time, either because new functionality has been exposed in the Rhino SDK or because a certain component makes a lot of sense to a lot of people. Adding pre-canned components that do the same as '8 or 10 components strung together' for the heck of it will balloon the total number of components everyone has to deal with. If you find yourself using the same 8 to 10 components together all the time, then please mention it on this forum. A lot of the currently existing components have been added because someone asked for it.
It’s not the primary components that catalyzed this thought but rather the secondary components. I was toying with a component today (twist from jackalope) that made use of three toggle components. The things they controlled are checkboxes in other apps.
Take a look at this jpg. Ignore differences; I did 'em quickly. GH required 19 components to do what SW did with 4 commands. Note the difference in screen real estate.
As an aside, I really hate SolidWorks (SW). But going forward, I’ll use it as an example because it’s what most people are familiar with.
"[...] has a far cleaner and more intuitive interface. So does SolidWorks, Inventor, CATIA, NX, and a bunch of others."
Again, GH was not designed to be an alternative to these sort of modellers. I don't like referring to GH as 'parameteric' as that term has been co-opted by relational modellers. I prefer to use 'algorithmic' instead. The idea behind parameteric seems to be that one models by hand, but every click exists within a context, and when the context changes the software figures out where to move the click to. The idea behind algorithmic is that you don't model by hand.
I agree, and disagree. I believe parametric applies equally to GH AND SW, NX, and so forth, while algorithmic is unique to GH (and GC and Dynamo I think). Thus I understand why you prefer the term. I too tend to not like referring to GH as a parametric modeler for the same reason.
But I think it oversimplifies it to say parametric modelers move the clicks. SW tracks clicks the same way GH does; GH holds that information in geometry components while SW holds it in a feature in the feature tree. In both GH and SW edits to the base geometry will drive a recalculation, but more commonly, it’s an edit to input data, beit equations or just plain numbers, that drive a recalculation.
I understand the difference in these programs. What brought me to GH is that it can create a visual dialog that standard modelers can’t. But as I've grown more comfortable with it I’ve come to realize that the GUI of GH and the GUI of other parametric modelers, while looking completely different, are surprisingly interchangeable. Do not misconstrue that I’m suggesting that GH should replace it’s GUI with SW’s. I’m not. I refrain from suggesting anything specific. I only suggest that you allow yourself to think radically.
This is not to say there is no value in the parametric approach. Obviously it is a winning strategy and many people love to use it. We have considered adding some features to GH that would make manual modelling less of a chore and we would still very much like to do so. However this is such a large chunk of work that we have to be very careful about investing the time. Before I start down this road I want to make sure that the choice I'm making is not 'lame-ass algorithmic modeller with some lame-ass parametrics tacked on' vs. 'kick-ass algorithmic modeller with no parametrics tacked on'.
Given a choice, I'd pick kick-ass algorithmic modeller with no parametrics tacked on.
2. Visual Programming.
I'm not exactly sure I understand your grievance here, but I suspect I agree. The visual part is front and centre at the moment and it should remain there. However we need to improve upon it and at the same time give programmers more tools to achieve what they want.
I'll admit, this is a bit tough to explain. As I've re-read my own comment, I think it was partly a precursor to the context sensitivity point and touched upon other stated points.
This now touches upon my own ignorance about GH’s target market. Are you moving toward a highly specialized tool for programmers and/or mathematicians, or is the intent to create a tool that most designers can master? If it’s the former, rock on. You’re doing great. If it’s the latter, I’m one of the more technically sophisticated designers I know and I’m lost most of the time when using GH.
GH allows the same freedom as a command line editor. You can do whatever you like, and it’ll work or not. And you won’t know why it works or doesn't until you start becoming a bit of an expert and can actually decipher the gibberish in a panel component. I often feel GH has the ease of use of DOS with a badass video card in front.
Please indulge my bit of storytelling. Early 3D modelers, CATIA, Unigraphics, and Pro-Engineer, were unbelievably difficult to use. Yet no one ever complained. The pain of entry was immense. But once you made it past the pain threshold, the salary you could command was very well worth it. And the fewer the people who knew how to use it, the more money you could demand. So in a sense, their lack of usability was a desirable feature among those who’d figured it out.
Then SolidWorks came along. It could only do a fraction of what the others did, but it was a fraction of the cost, it did most of what you needed, and anyone could figure it out. There was even a manual on how to use it. (Craziness!) Within a few short years, the big three all had to change their names (V5, NX, and Wildfire (now Creo)) and change the way they do things. All are now significantly easier to use.
I can tell that the amount of development time that’s gone into GH is immense and I believe the functionality is genius. I also believe it’s ease of use could be greatly improved.
Having re-read my original comments, I think it sounded a bit snotty. For that I apologize.
3. Context sensitivity.
"There is no reason a program in 2014 should allow me to make decisions that will not work. For example, if a component input is in all cases incompatible with another component's output, I shouldn't be able to connect them."
Unfortunately it's not as simple as that. Whether or not a conversion between two data types makes sense is often dependent on the actual values. If you plug a list of curves into a Line component, none of them may be convertible. Should I therefore not allow this connection to be made? What if there is a single curve that could be converted to a line? What if you want to make the connection now, but only later plan to add some convertible curves to the data? What you made the connection back when it was valid, but now it's no longer valid, wouldn't it be weird if there was a connection you couldn't make again?
I've started work on GH2 and one of the first things I'm writing now is the new data-conversion logic. The goal [...] is to not just try and convert type A into type B, but include information about what sort of conversion was needed (straightforward, exotic, far-fetched. etc.) and information regarding why that type was assigned.
You are right that under some conditions, we can be sure that a conversion will always fail. For example connecting a Boolean output with a Curve input. But even there my preferred solution is to tell people why that doesn't make sense rather than not allowing it in the first place.
You bring up both interesting points and limits to my understanding of coding. I’ve reached the point in my learning of GH where I’m just getting into figuring out the sets tab (and so far I’m not doing too well). I often find myself wondering “Is all of this manual conditioning of the data really necessary? Doesn’t most software perform this kind of stuff invisibly?” I’d love to be right and see it go away, but I could easily be wrong. I’ve been wrong before.
5. Components.
"Give components a little “+” or a drawer on the bottom or something that by clicking, opens the component into something akin to a dialog box. This should give access to all of the variables in the component. I shouldn't have to r-click on each thing on a component to do all of the settings."
I was thinking of just zooming in on a component would eventually provide easier ways to access settings and data.
I kinda like this. It’s a continuation of what you’re currently doing with things like the panel component.
"Could some of these items disappear if they are contextually inappropriate or gray out if they're unlikely?"
It's almost impossible for me to know whether these things are 'unlikely' in any given situation. There are probably some cases where a suggestion along the lines of "Hey, this component is about to run 40,524 times. It seems like it would make sense to Graft the 'P' input." would be useful.
6. Integration.
"Why isn't it just live geometry?"
This is an unfortunate side-effect of the way the Rhino SDK was designed. Pumping all my geometry through the Rhino document would severely impact performance and memory usage. It also complicates the matter to an almost impossible degree as any command and plugin running in Rhino now has access to 'my' geometry.
"Maybe add more Rhino functionality to GH. GH has no 3D offset."
That's the plan moving forward. A lot of algorithms in Rhino (Make2D, FilletEdge, Shelling, BlendSrf, the list goes on) are not available as part of the public SDK. The Rhino development team is going to try and rectify this for Rhino6 and beyond. As soon as these functions become available I'll start adding them to GH (provided they make sense of course).
On the whole I agree that integration needs a lot of work, and it's work that has to happen on both sides of the isle.
You work for McNeel yet you seem to speak of them as a separate entity. Is this to say that there are technical reasons GH can only access things through the Rhino SDK? I’d think you would have complete access to all Rhino API’s. I hope it’s not a fiefdom issue, but it happens.
7. Documentation.
Absolutely. Development for GH1 has slowed because I'm now working on GH2. We decided that GH1 is 'feature complete', basically to avoid feature creep. GH2 is a ground-up rewrite so it will take a long time until something is ready for testing. During this time, minor additions and of course bug fixes will be available for GH1, but on a much lower frequency.
Documentation is woefully inadequate at present. The primer is being updated (and the new version looks great), but for GH2 we're planning a completely new help system. People have been hired to provide the content. With a bit of luck and a lot of work this will be one of the main selling points of GH2.
It begs the question that I have to ask. When is GH1.0 scheduled to launch? And if you need another person to proofread the current draft of new primer.
patrick@girgen.com
I can’t believe wikipedia has an entry for feature creep. And I can’t believe you included it. It made me giggle. Thanks.
8. 2D-ness.
"I know you'll disagree completely, but I'm sticking to this. How else could an omission like offsetsurf happen?"
I don't fully disagree. A lot of geometry is either flat or happens inside surfaces. The reason there's no shelling (I'm assuming that's what you meant, there are two Offset Surface components in GH) is because (a) it's a very new feature in Rhino and doesn't work too well yet and (b) as a result of that isn't available to plugins.
I believe it’s been helpful for me to have figured this out. I recently completed a GH course at a local Community College and have done a bunch of online tutorials. The first real project I decided to tackle has turned out to be one of the more difficult things to try. It’s the source of the questions I posted. (Thanks for pointing out that they were posted in the wrong spot. I re-posted to the discussions board.)
I just can't seem to figure out how to turn the voronoi into legitimate geometry. I've seen this exact question posted a few times, but it’s never been successfully answered. What I'm showing here is far more angular than I’m hoping for. The mesh is too fine for weaverbird to have much of an effect. And I haven't cracked re-meshing. Btw, in product design, meshes are to be avoided like the plague. Embracing them remains difficult.
As for offsetsurf, in Rhino, if you do an offsetsurf to a solid body, it executes it on all sides creating another neatly trimmed body thats either larger or smaller than the original. This is how every other app I know of works. GH’s offsetsurf creates a bunch of unjoined faces spaced away from the original brep. A common technique for 3D voronois (Yes, I hit the voronoi overuse easter egg) is to find the center of each cell and scale them by this center. If you think about it, this creates a different distance from the face of the scaled cell to the face of the original cell for every face. As I've mentioned, this project is giving me serious headaches.
Don't get me wrong, I appreciate the feedback, I really do, but I want to be honest and open about my own plans and where they might conflict with your wishes. Grasshopper is being used far beyond the boundaries of what we expected and it's clear that there are major shortcomings that must be addressed before too long. We didn't get it right with the first version, I don't expect we'll get it completely right with the second version but if we can improve upon the -say- five biggest drawbacks (performance, documentation, organisation, plugin management and no mac version) I'll be a happy puppy.
--
David Rutten
Thank you for taking the time to reply David. Often we feel that posting such things is send it into the empty ether. I’m very glad that this was not the case.
And thank you for all of the work you've put into GH. If you found any of my input overly harsh or ill-mannered, I apologise. It was not my intent. I'm generally not the ranting sort. If I hadn't intended to provide possibly useful input, I wouldn't have written.
Cheers
Patrick Girgen
Ps. Any pointers on how to get a bit further on the above project would be greatly appreciated.
…
e chosen to dive into Grasshopper. I’m about 6 months in. If some of my comments are completely off, please take that to mean that a feature is too inaccessible to a newish user rather that it’s just missing, as I may have stated.
One of my primary pain points is this. Things that can be done in other programs are invariably easier in other programs. This is a big enough issue that I doubt there’s an easy solution that an armchair qb like myself can offer up.
The interface:
I’ve used a lot of 3D programs. I’ve never encountered one as difficult as grasshopper. What in other programs is a dialog box, is 8 or 10 components strung together in grasshopper. The wisdom for this I often hear among the grasshopper community is that this allows for parametric design. Yet PTC (Parametric Technology Corp.) has been doing parametric design software since 1985 and has a far cleaner and more intuitive interface. So does SolidWorks, Inventor, CATIA, NX, and a bunch of others.
In the early 2000's, when parametric design software was all the rage, McNeel stated quite strongly the Rhino would remain a direct modeler and would not become a parametric modeler. Trends come. Trends go. And the industry has been swinging back to direct modeling. So McNeel’s decision was probably ok. But I have to wonder if part of McNeel’s reluctance to incorporate some of the tried and proven ideas of other parametric packages doesn't have roots in their earlier declaration to not incorporate parametrics.
A Visual Programming Language:
I read a lot about the awesomeness and flexibility of Grasshopper being a visual programming language. Let’s be clear, this is DOS era speak. I believe GH should continue to have the ability to be extended and massaged with code, as most design programs do. But as long as this is front and center, GH will remain out of reach to the average designer.
Context sensitivity:
There is no reason a program in 2014 should allow me to make decisions that will not work. For example, if a component input is in all cases incompatible with another component's output, I shouldn't be able to connect them.
Sliders:
I hate sliders. I understand them, but I hate ‘em. I think they should be optional. Ya, I know I can r-click on the N of a component and set the integer. It’s a pain, and it gives no feedback. The “N” should turn into the number if set. AAAnd, sliders should be context sensitive. I like that the name of a slider changes when I plug it into something. But if I plug it into something that'll only accept a 1, a 2, or a 3, that slider should self set accordingly. I shouldn't be able to plug in a “50” and have everything after turn red.
Components:
Give components a little “+” or a drawer on the bottom or something that by clicking, opens the component into something akin to a dialog box. This should give access to all of the variables in the component. I shouldn't have to r-click on each thing on a component to do all of the settings.
And this item I’m guessing on. I’m not yet good enough at GH to know if this may have adverse effects. Reverse, Flatten, Graft, etc.; could these be context sensitive? Could some of these items disappear if they are contextually inappropriate or gray out if they're unlikely?
Tighter integration with Rhino:
I'm not entirely certain what this would look like. Currently my work flow entails baking, making a few Rhino edits, and reinserting into GH. I question the whole baking thing, btw. Why isn't it just live geometry? That’s how other parametric apps work. Maybe add more Rhino functionality to GH. GH has no 3D offset. I have to bake, offsetserf, and reinsert the geometry. I’m currently looking at the “Geometry Cache” and “Geometry Pipeline” components to see if they help. But I haven't been able to figure it out. Which leads me to:
Update all of the documentation:
I'm guessing this is an in process thing and you're working toward rolling GH from 0.9.00075 to 1.0. GH was being updated nearly weekly earlier this year. Then it suddenly stopped. If we're talking weeks before a full release, so be it. But if we're looking at something longer, a documentation update would help a lot. Geometry Cache and Geometry Pipeline’s help still read “This is the autogenerated help topic for this object. Developers: override the HtmlHelp_Source() function in the base class to provide custom help.” This does not help. And the Grasshopper Primer 2nd Ed. was written for GH 0.60007.
Grasshopper is fundamentally a 2D program:
I know you'll disagree completely, but I'm sticking to this. How else could an omission like offsetsurf happen? Pretty much every 3D program in existence has this. I’m sure I can probably figure out how to deconstruct the breps, join the curves, loft, trim, and so forth. But does writing an algorithm to do what all other 3D programs do with a dialog box seem reasonable? I'm sure if you go command by command you'll find a ton on such things.
If you look at the vast majority of things done in GH, you'll note that they're mostly either flat or a fundamentally 2D pattern on a warped surface.
I've been working on a part that is a 3D voronoi trimmed to a 3D model. I've been trying to turn the trimmed voronoi into legitimate geometry for over a month without success.
http://www.grasshopper3d.com/profiles/blogs/question-voronoi-3d-continued
I’ve researched it enough to have found many others have had the exact same problem and have not solved it. It’s really not that conceptually difficult. But GH lacks the tools.
Make screen organization easier:
I have a touch of OCD, and I like my GH layout to flow neatly. Allow input/output nodes to be re-ordered. This will allow a reduction in crossed wires. Make the wire positions a bit more editable. I sometimes use a geometry component as a wire anchor to clean things up. Being able to grab a wire and pull it out of the way would be kinda nice.
I think GH has some awesome abilities. I also think accessing those abilities could be significantly easier.
~p…
re are major changes and enhancements.
HONEYBEE
More Flexible Workflow - Many small modifications were made to support a more flexible workflow, such as the ability to separate a zone created with masses2Zones into editable HBSrfs that can be recombined. For the energy components, it is now possible to plug custom constructions directly into the components that set the zone constructions without writing them first into the library. For the daylighting components it is now possible to change all of the materials of specific surface types at once.
Support for Complex Geometry - Many small bugs for complex geometry have been fixed including the ability to import energy results correctly for curved NURBS surfaces as well as unconventional window configurations. Also, the intersectMasses component now almost always succeeds in splitting all of the surfaces of adjacent zones, no matter how complex the intersection is.
Automatic Download Issues Fixed - Many users who faced issues with not having “gendaymtx.exe” or who had trouble syncing with our github know that we faced an issue with automatic background downloads.
Air Walls - Honeybee EnergyPlus models now officially support air walls (or virtual partitions) in a basic implementation. Now, any time that you use the air wall construction or set a surface type to “air wall,” the air between adjacent zones will be automatically mixed. At present, this mixing is just a constant flow based on the surface area between zones connected by air walls multiplied by an adjustable “flow factor.” It is important to stress that this basic air mixing is not with the EnergyPlus Airflow Network, although the groundwork laid in this release will eventually allow for the implementation of the Airflow Network in future releases. As such, this present air mixing is only suitable for multi-zone conditions where there is not significant buoyancy-driven flow between zones.
Natural Ventilation - To go along with the new potential introduced by air walls, there has been a basic implementation of EnergyPlus’s natural ventilation objects in a new component called “Set EP Airflow”. The current setup allows for three possible types of natural ventilation: 1) natural ventilation through windows (with auto-calculated flow based on window area, outdoor wind speed/direction, and stack effects), 2) custom wind and stack objects that can be used to model things such as chimneys off of single zones, and 3) constant, fan-driven natural ventilation.
Additional Thermal Mass - The capability to add additional thermal mass to zones has been added. This is useful for factoring in the mass of indoor furniture or heavy interior objects such as chimneys.
New Utility Components - Abraham has added a couple of useful components to help calculate lighting loads based on bulb types and target lighting levels as well as a converter from ACH to the m3/s-m2 that the other HB components accept. Along this vein, there is also a component for adding in the resistance of Air Films to HB constructions.
Improved and Editable Ideal Air Loads System - The EnergyPlus Ideal Air System now goes through an automatic sizing period at the start of the simulation based on the extreme weeks of the weather file. Furthermore, the ability to adjust many of the parameters of the ideal air loads system have been added with a new “Set Ideal Air Loads Parameters” component. The component allows you to add in heat recovery, air side economizers and demand-controlled ventilation.
OpenStudio Export Update - The OpenStudio workflow is still largely under development but this release includes a version with a working VAV and PTHP system template for those curious with experimenting. Note that not all of the new features available for the basic “Run Energy Simulation” component are available for the OpenStudio component (such as air walls, natural ventilation, or additional thermal mass).
Microclimate/Indoor Comfort Maps - Blossoming from initial experiments with the radiant temperature map, a workflow for looking into sub-zone microclimate and indoor comfort has been initiated. All components for this are presently under the Honeybee WIP tab but, over the next month, they will be completing their development phase and moving into the rest of the tabs. If you are interested in testing when they are ready, please let Chris know. For a teaser video of the intended capabilities, see this video: (https://www.youtube.com/watch?v=fNylb42FPIc&list=UUc6HWbF4UtdKdjbZ2tvwiCQ)
LADYBUG
Monthly Bar Chart - After much demand from multiple parties, a new component to create monthly bar and line charts has been added. The component is particularly useful for plotting the outputs of the “Average Data” component like monthly EPW data or averaged monthly-per hour data. It also supports daily data and any type of Energy simulation results.
Wind Profile - To go along with the new capabilities of natural ventilation in Honeybee, Ladybug now has a fully fleshed-out Wind Profile component that allows you to visualize how wind speed changes with height in relation to your building geometry. The component is geared to understanding the conditions of prevailing wind and will be useful in the future for setting up CFD models. Credit goes to Djordje Spasic for adding in all of the new capabilities. In a similar vein, the appearance of the wind rose has also been improved thanks to suggestions from Alejandra Menchaca.
Faster Solar Adjusted Temperature - Thanks to the SolarCal method from the Center for the Built Environment at UC Berkeley (http://escholarship.org/uc/item/89m1h2dg), the solar adjusted temperature component now includes an option for a much faster calculation that produces results that are very close to those originally obtained with the genCumSky component. Instead of using the cumulative sky, the component can now accept the direct and diffuse radiation from the ImportEPW component. Over a whole year, this essentially takes a calculation that used to be a half-hour and shrinks it down to 10 seconds. Thanks again to those at UC Berkeley for keeping their work open source!
Instructions - Last but not the least, [It took me almost two years to understand this but finally] we have a text file that describes the installation step by step and is way easier to modify than a video. You can find it in the zip file. Credit goes to Chris!
We also want to welcome Anton, Patrick and Sandeep to the team. Anton has kicked off his development by working on a component to import and visualize epw ground temperature data and he will be continuing to develop components to bring in reliable precipitation data to Ladybug. With this basis, he will continue to implement Honeybee components for ground heat storage, earth tubes, rain collection and hot water systems. Patrick and Sandeep are working on integration of Honeybee to Energy Performance Calculator.
As always let us know your comments and suggestions.
Enjoy!…
ives that have been shared so far.
Intersect Shouldn't Punt When Encountering Areas of Intersection
Several posts talk about how Booleans are really just shortcut implementations of the Intersect/Trim/Split/Join (ITSJ) design pattern. Agreed. I realized this when trying to understand and resolve my first Boolean related problem. So when I broken down my characterization to the 4 component steps, I found is that it was the Intersect operation that was generating an erroneous (read: incomplete) set of intersection curves. I posted my findings along with a possible solution in an email to McNeel tech support and in this Rhino discussion an edited version of which I’ve quoted again below. But the only response I received from McNeel was that I shouldn't expect any changes in the product that improves Booleans.
The unexpected behavior I've been having with Rhino, and by extension Grasshopper, is that the current implementation of the Rhino Intersect command is generating an incomplete network of curves when given 2 surfaces having regions that are (almost) coincident. When Intersect determines that there's no single curve able to represent the intersection in those areas, but rather an area of intersection, Intersect erroneously doesn't generate any curve to represent that portion of the intersection — which is mathematically incorrect. This decision to "punt" in these situations renders the generated results to not be useful for subsequent steps of the ITSJ design pattern. Rather than not including these areas of intersection in the network of curves, Intersect should generate any non-kinky, non-looping curve(s) through a region of intersection that connects with all other intersection curves adjacent to the region. Any valid curve is far more useful — and mathematically correct — than no curve through these regions.
Informative and Detailed Error Reporting Will Save Users’ Time
A number of users feel as I do that the error information available when an operation fails is insufficient.
The Rhino Learning Curve Is Fractally Steep
While some responses have suggested that I’m just too new to Rhino, a number of long-time Rhino users have said that they are continually “learning” the product's idiosyncrasies, and expect that they will never really know what the product will do every time. What they’ve learned from their years of experience is how to hack their designs to work around Rhino’s quirks.
I conclude from these stories that, sure, I’m green, but that I, all of us, are destine to be forever “green” because the current development methodology results in a product that can never really be understood.
Wow.
In his reply above @Paul N Jeffies said…
One thing that's important to understand when using Rhino for this kind of thing is that Rhino does not have a particularly meaningful conception of a 'solid object' - solids are defined simply as a collection of (infinitely thin) NURBS surfaces joined together with no gaps between. That's part of the reason for the problems with booleans in Rhino, but it also means that you don't really need boolean operations since you can do everything by exploding the polysurface and using the Intersect/Trim/Split commands on the individual surfaces to build up the boundary surfaces you want, then rejoin into a solid afterwards.
As a software architect with ~40 years of tech experience, I would again suggest that the root cause of the product's unknowability is the lack of rigor so far exhibited in defining the layers of abstraction. If proper rigor were applied, then, from a user’s perspective, a solid really would be a solid. The proper way to reduce a solid to a set of adjacent surfaces would be to use a function like ExplodeSolid, and to get a set of curves from a surface we would have to use ExplodeSurface, and so on. So rigor doesn’t prohibit users from pulling back the curtain, but rather empowers the core development team to enforce encapsulation at the current layer of abstraction — whether point, curve, surface, solid, or whatever.
The Solution Begins With Changing The Conversation
With all this said, I don’t believe that Rhino is fatally flawed or impossible to fix. I also don't believe that the resulting loss of productivity is the users' fault. I do believe though that the first step is for all, McNeel and users, to name the condition, raise this as a high priority, work collaboratively to define a corrected abstraction stack, and add appropriate rigor to the implementation of the next major release.
About a month ago I spent about 1/2 hour searching through the Rhino discussions for topics related to The Boolean Problem. I found literally 100's of posting, with many noops like I am now saying they were giving up and going to another tool because Rhino’s learning curve was too steep. Yes, filleting and trimming are two other big Rhino problems that I believe have similar roots. Yet I wonder whether these deep-seated challenges could, in fact, be overcome — by first changing the conversation.
I’d again ask what other, more experienced users think.
- Bob…
Added by neobobkrause at 2:49pm on October 4, 2016
st list, shortest list, cross reference) in cases where the number of iterations has to be kept track of and used in the code.
I am developing a number of components that instantiate objects of a custom class type (which I define), and add the object's parameters to a database for use in other applications. In almost all cases my classes have an ID parameter, which I typically set in the SolveInstance method using an int variable which is incremented after each object's instantiation. I'd like to be able to access or keep track of the number of iterations without having to register my params as GH_ParamAccess.tree, and looping over one of the input trees.
I've included a simple example to illustrate the point. I define a simple class that takes two numbers as inputs, adds them, and includes an ID attribute:
public class AddTwoNumbers {
//Basic addition parameters
public string ID = "not set";
public double A;
public double B;
public double C;
//Addition method
public void Add()
{
C = A + B;
}
//Constructor
public AddTwoNumbers(double a, double b)
{
A = a;
B = b;
this.Add();
}
}
If I do not register my param access as .tree, I am not able to increment the ID each time through the SolveInstance. Here are my SolveInstance and RegisterInputParams methods using GH's iteration:
protected override void RegisterInputParams(GH_Component.GH_InputParamManager pManager) {
pManager.Register_DoubleParam("Double A", "A", "First number to add.");
pManager.Register_DoubleParam("Double B", "B", "Second number to add.");
}
protected override void SolveInstance(IGH_DataAccess DA) {
//local variables to catch incoming data
double myA = 0.0;
double myB = 0.0;
//assign incoming data to local variables
if (!DA.GetData(0, ref myA)) { return; }
if (!DA.GetData(1, ref myB)) { return; }
//instantiate a new AddTwoNumbers object
AddTwoNumbers myAdd = new AddTwoNumbers(myA, myB);
//give this object an ID
// ??? how do we assign a numerical ID if we don't have access to an iterator?
//add the object to a static list in this namespace - not implemented here for simplicity's sake
//a string to report all of myAdd's parameters
string myParams = myAdd.ID + ", " + myAdd.A.ToString() + ", " + myAdd.B.ToString() + ", " + myAdd.C.ToString();
//set output data
DA.SetData(0, myParams);
}
and a screenshot of the component in action:
If I do register my params as .tree, I am able to increment an ID variable each time through my nested for loop, but I'd have to do a lot of work to account for all of the possible input scenarios (an item and a list, 2 lists of different lengths, a list and a tree, etc.). Here are my SolveInstance and RegisterOutputParams methods, minus all of the defense, and a screenshot of this component:
protected override void RegisterInputParams(GH_Component.GH_InputParamManager pManager) {
pManager.Register_DoubleParam("Double A", "A", "First number to add.", GH_ParamAccess.tree);
pManager.Register_DoubleParam("Double B", "B", "Second number to add.", GH_ParamAccess.tree);
}
protected override void SolveInstance(IGH_DataAccess DA) {
//local variables to catch incoming data
GH_Structure<GH_Number> myATree = new GH_Structure<GH_Number>();
GH_Structure<GH_Number> myBTree = new GH_Structure<GH_Number>();
//An output data tree
DataTree<string> myOutTree = new DataTree<string>();
//An iterator counter
int IteratorCounter = 0;
//pass incoming data into local variables
if (!DA.GetDataTree(0, out myATree)) { return; }
if (!DA.GetDataTree(1, out myBTree)) { return; }
//pick a data tree to loop over - since we don't know which tree is larger, we'd have to
//do a bunch of defensive programming here. In this case we'll just loop over the A tree
for (int i = 0; i < myATree.Branches.Count; i++)
{
//set the output path = to the incoming path
GH_Path myOutPath = new GH_Path(myATree.Paths[i]);
//loop over each item in the branch
for (int j = 0; j < myATree.Branches[i].Count; j++)
{
//instantiate a new AddTwoNumbers object
AddTwoNumbers myAdd = new AddTwoNumbers(myATree.Branches[i][j].Value, myBTree.Branches[i][j].Value);
//here we assume that that the Btree will be of identical structure ... of course this might not be the case
//again, we could do a bunch of defense here, but we'd like to be able to use GH's iteration.
//give this object an ID
myAdd.ID = IteratorCounter.ToString();
//now since we have access to a counter, we can assign IDs using that counter. Since the counter is
//incremented each time through the loop, we know we'll never get a duplicate ID.
//add the object to a static list in this namespace - not implemented here for simplicity's sake
//a string to report all of myAdd's parameters
string myParams = myAdd.ID + ", " + myAdd.A.ToString() + ", " + myAdd.B.ToString() + ", " + myAdd.C.ToString();
//add the string to the out tree
myOutTree.Add(myParams, myOutPath);
//increment the counter
IteratorCounter++;
}
}
I think this is a specific breed of a more general question: what are the scenarios under which GH's built in iteration will not suffice? When do you need to specify the GH_ParamAccess and take control of the iteration? Another example: sometimes you need to access and use branch paths in a component's code ... can you do this without setting the access to .tree?
Any help would be greatly appreciated. Thanks!
PS - I included a .zip of my visual studio 2010 project, in case anyone would like to take a closer look.
…
g of over 150 annotated Grasshopper definitions and representations of their potential for the beginning to advanced Grasshopper user. The site brings together ongoing parametric research through the fields of Architecture, Landscape Architecture, Fabrication and Structure.
Summer 2014 Additions Include:
…
using Grasshopper.Kernel.Data; using Grasshopper.Kernel.Types;
using System; using System.IO; using System.Xml; using System.Xml.Linq; using System.Linq; using System.Data; using System.Drawing; using System.Reflection; using System.Collections; using System.Windows.Forms; using System.Collections.Generic; using System.Runtime.InteropServices;
/// <summary> /// This class will be instantiated on demand by the Script component. /// </summary> public class Script_Instance : GH_ScriptInstance { #region Utility functions /// <summary>Print a String to the [Out] Parameter of the Script component.</summary> /// <param name="text">String to print.</param> private void Print(string text) { /* Implementation hidden. */ } /// <summary>Print a formatted String to the [Out] Parameter of the Script component.</summary> /// <param name="format">String format.</param> /// <param name="args">Formatting parameters.</param> private void Print(string format, params object[] args) { /* Implementation hidden. */ } /// <summary>Print useful information about an object instance to the [Out] Parameter of the Script component. </summary> /// <param name="obj">Object instance to parse.</param> private void Reflect(object obj) { /* Implementation hidden. */ } /// <summary>Print the signatures of all the overloads of a specific method to the [Out] Parameter of the Script component. </summary> /// <param name="obj">Object instance to parse.</param> private void Reflect(object obj, string method_name) { /* Implementation hidden. */ } #endregion
#region Members /// <summary>Gets the current Rhino document.</summary> private readonly RhinoDoc RhinoDocument; /// <summary>Gets the Grasshopper document that owns this script.</summary> private readonly GH_Document GrasshopperDocument; /// <summary>Gets the Grasshopper script component that owns this script.</summary> private readonly IGH_Component Component; /// <summary> /// Gets the current iteration count. The first call to RunScript() is associated with Iteration==0. /// Any subsequent call within the same solution will increment the Iteration count. /// </summary> private readonly int Iteration; #endregion
/// <summary> /// This procedure contains the user code. Input parameters are provided as regular arguments, /// Output parameters as ref arguments. You don't have to assign output parameters, /// they will have a default value. /// </summary> private void RunScript(bool bake, List<GeometryBase> G, Point3d L, Color C) { COL = C; LOCATION = L; NAME = ""; pnts.Clear(); crvs.Clear(); breps.Clear();
foreach(GeometryBase geom in G){ switch(geom.GetType().Name){ case "Point": pnts.Add(((Rhino.Geometry.Point) geom).Location); break; case "Curve": //create a new geometry list for display break; case "PolyCurve": crvs.Add((PolyCurve) geom); break; case "Brep": breps.Add((Brep) geom); break; default: Print("Add a new case for this type: " + geom.GetType().Name); break; } }
if(bake){ Rhino.DocObjects.InstanceDefinition I = doc.InstanceDefinitions.Find(NAME, false);
if(I != null) doc.InstanceDefinitions.Delete(I.Index, true, true);
int index = doc.InstanceDefinitions.Add(NAME, "description", Point3d.Origin, G); doc.Objects.AddInstanceObject(index, Transform.Scale(L, 1)); } }
// <Custom additional code> //GEOMETRY Lists to display
List<Point3d> pnts = new List<Point3d>(); List<PolyCurve> crvs = new List<PolyCurve>(); List<Brep> breps = new List<Brep>();
string NAME; Point3d LOCATION; int THICKNESS = 2; Color COL;
//Return a BoundingBox that contains all the geometry you are about to draw. public override BoundingBox ClippingBox { get { return BoundingBox.Empty; } } //Draw all meshes in this method. public override void DrawViewportMeshes(IGH_PreviewArgs args) {
}
//Draw all wires and points in this method. public override void DrawViewportWires(IGH_PreviewArgs args) { foreach(Point3d p in pnts) args.Display.DrawPoint(p, Rhino.Display.PointStyle.ControlPoint, THICKNESS, COL);
foreach(PolyCurve c in crvs) args.Display.DrawCurve(c, COL, THICKNESS);
foreach(Brep b in breps) args.Display.DrawBrepShaded(b, new Rhino.Display.DisplayMaterial(COL));
args.Display.DrawPoint(LOCATION, Rhino.Display.PointStyle.ActivePoint, 3, Color.Black); args.Display.Draw3dText(NAME, Color.Gray, new Plane(LOCATION, Vector3d.ZAxis), THICKNESS / 3, "Arial"); }
// </Custom additional code> }…