F# Procedural Modelling and Z3 Constraint Solving

Matthew @moloneymb Moloney is excited by the potential of interactive F# coding in Revit.

The current implementation consists of a Revit add-in, like the Tsunami Rhino plugin, with a number of improvements.

Mantis is similar to the Revit Python Shell but for the F# programming language. This brings with it a number of specific advantages including full code completion, error checking, performance, and design scalability.

Interactive F# Mantis shell in Revit

You can I try it out yourself in beta.

Let Matt know if you need any help getting started.

Feedback would be greatly appreciated.

The use of functionally generated content for structures opens the door to a wonderful world of potential, freeing up the designer from the mundane while still being able to scale to complex models that Visual BIM systems have such a hard time with.

Says Matt:

If something like Mantis helps, I'd like to continue working in the space. I have a ton of additional ideas for things to build on top of it – e.g., procedural generation libraries, the Z3 constraint solver, using type providers to import product catalogues, etc. I can even do an Rx Observable graph to update objects based on UI controls which would allow for interactive / live updates similar to the Dynamo experience. Instead of embedding code in a graph you embed the graph in the code and only visualize the UI inputs if and when you need them. It would be a code first approach. All of this is possible right out of the box with Mantis. I just need to explain and give demos on how it can be done :)

This is an experiment to see if advanced language techniques is something architects actually want. I can build stuff just fine a vacuum by myself but there is little point to that :) I'm not in the business of building buildings so I can't make use of it myself. Much better to be helping other people.

Which means that I need feedback on the basics before I can justify investing more time into it. If it doesn't look like it will get much traction then I'll focus on something else.

It is ideal for users:

More background information from Matt:

Examples in Procedural Modelling

Most of these approaches use an external domain-specific language (DSL) that gets interpreted. External DSLs are hard to extend, domain specialise, and compose - things that you almost always want to do. For example, you could take a building DSL and an arch DSL one to make a gothic building DSL that uses lots of archways. Using a functional programming language you can use internal DSLs that are trivial to extend, compose, and domain specialise to your specific domain as it is all written in the same language.

Z3 Constraint Solver

The Z3 Constraint Solver is mostly only used by academics and there is not much information out there on how to use it in other domains. In effect, it is an efficient way to automate a set of tedious tasks that would normally take far too long for a computer to figure out but is now way faster due to all the great research done in generalised solvers. Solvers used to be poor quality and very expensive but Microsoft recently made one of the best solvers available for free as open source. An example application would be to build your own routing algorithm for industrial piping that could take your specific inputs into account. E.g. available parts, budget, safety, and regulations. If you move a tank you can just rerun the route function and the rest is automatic.

Type Provider Product catalogue

Instead of going to a website and manually doing a search for a component you can simply find and reference the model directly in the code as if you already had it and wrapped it in an API. For instance, instead of downloading and managing shared folders of models and then referencing the models in functions via error prone path strings the type provider will do the fetching, caching, and loading the model behind the scenes. The API for this is exposed via static members e.g. Catalog.Kitchen.Sink2. If Sink3 is later added to the catalogue it's easy to change to the new sink, as it will appear as another static parameter. If Sink2 is later removed from the online catalogue (because it is no longer made) then the static member will cease to exist and the code will no longer compile.

Example Type Provider: