
Download Script:
Download .3dm File:
Aim & Concept

Why I Created This Script
In my studio project, I’m designing a space with an atrium that spans multiple floors, where footbridges are needed to connect the floors. However, the width of the atrium changes, meaning each bridge would have to be modeled differently.

Manually adjusting each bridge would take hours—and every time something changed, I’d have to start over. I needed a faster, more flexible solution that would allow me to quickly adapt the design without losing control over the details.
Why This Script Saves Time
Instead of manually adjusting widths, thicknesses, and heights, I can do everything with one simple click:
✔ Change the bridge length to match the atrium.
✔ Change the bridge width to create a more dynamic space.
✔ Adjust the floor thickness depending on material needs.
✔ Modify the handrail height and curvature for different conditions.
✔ Refine the walls – their shape, height, and curvature are all parametric.
✔ Adapt the timber panel size of the walls.
Since my project involves multiple footbridges, this script makes it possible to update all of them instantly without having to remodel each one. It transforms a time-consuming process into a flexible, dynamic workflow.
The Steps
How It Works
The script generates a footbridge using just points: the start, middle (can be multiple), and end. From these points, the script automatically constructs the bridge and gives me control over multiple aspects of the design.
It produces four key outputs:
- The floor slab – The walking surface of the bridge.
- The bridge walls – Defining the structure’s enclosure.
- The handrail – Adjustable in height, curvature, and offset from the walls.
- The timber panels – A modular system of triangular panels that can be resized and adapted.
Step 1: Creating the Bridge Floor Slab

The first step in my parametric bridge script is generating the bridge’s floor slab—the main surface people will walk on.
1. Setting the Base Points
- The script begins with multiple points that define the shape of the bridge.
- Using the Interpolated Curve component, I connect these points to form a smooth path for the bridge.
2. Mirroring the Curve & Adjusting Width Efficiently
- I create a YZ Plane using the start point of the bridge.
- To control the position of the Plane, I use the List Item component to select the start point and move it to the middle of the bridge’s width.
- This approach does two things at once:
✔ It mirrors the curve.
✔ It allows adjusting the bridge width.
This makes the script shorter and more efficient, reducing unnecessary components while increasing flexibility.
3. Generating the Floor Slab Surface
- With both curves in place, I use the Ruled Surface component to create a surface between them.
- Then, I extrude this surface to give it thickness, producing the first bakeable output of my script:
The extruded bridge floor slab.
Conclusion: My Learning Process and Future Improvements
At this stage, I already have a parametric floor slab that responds to different point positions, widths, and spans. This part of the script was quite simple and I didn’t run into any issues, but some potential options for it would be to use the Box component (by setting the Domain of the box and its Base Plane). This would be any easier option if the desired output is a more rectilinear design.
Option 1: create a curved floorslab using a Ruled Surface (see image above)
Option 2: create a rectangular floorslab using a Box (issue: the length of the box is defined by a slider and not by the start and end points of the bridge, which does not correspond to my concept)

Option 3: the tedious approah would be to manually create a box extrusion. (issue: the extrusion is defined by the start and end points of the bridge as desired, but this script is simply too tedious)

Step 2: Deconstructing the Floor Slab for Further Use
With the floor slab created, the next step is to break it down into its components so that different parts of the bridge can be constructed efficiently.
1. Using the Deconstruct Brep Component
- The Deconstruct Brep component allows me to extract the faces, edges, and vertices of the floor slab.
- Instead of manually defining new geometry, I can reuse the existing floor slab to drive the next steps in the script.
2. Selecting the Needed Items
- By filtering specific faces and edges, I ensure that I only extract what is needed for the next steps.
- To continue to the next step the following must be selected:
The bottom face of the slab → used in Step 3A to create the timber slats.
The outer (width of the bridge) edges of the slab → used in Step 3B to begin constructing the bridge walls.
This approach keeps the script efficient—instead of creating new reference geometry, everything is linked to the existing slab, ensuring that if any changes are made (e.g., adjusting width or thickness), the updates flow through the rest of the design.
Step 3A: Creating the Timber Slats

Now that the bottom face of the floor slab has been extracted in Step 2, we can use it as the base for generating the timber slats.
1. Using the Contour Component to Generate Slat Lines
- The Contour component is used to create evenly spaced section lines across a surface.
- Inputs for the Contour component:
Surface (Face): The bottom face of the floor slab (selected in Step 2).
Distance Between Contours: Controlled with a slider, allowing easy adjustments to the slat spacing. - The output of the Contour component is a set of parallel lines that represent the base of each slat.
2. Extruding the Contour Lines into Surfaces
- The contour lines are first extruded in the Z direction, turning them into surfaces.
3. Creating the Final Closed Timber Slats
- The surfaces are extruded once more in the thickness direction to create solid timber slats.
- This results in closed extrusions, making them ready for fabrication or rendering.
The result is a set of timber slats that can be adjusted by modifying the contour spacing slider. The slats can now be baked into Rhino as solid objects.
Step 3B: Creating a Set of Curves to Serve as the Base for the Bridge Walls

This was probably the most challenging step for me because it involved working with data trees—which are essential in Grasshopper when dealing with structured lists of points, curves, and surfaces. Instead of treating all geometry as a single flat list, data trees allow us to work with hierarchical relationships
1. Generating the Middle Axis of the Bridge
- First, I extract the midpoints of the two width-side edges of the floor slab.
- Using these points, I interpolate a curve to create a middle axis for the bridge.
- This axis acts as the spine for the perpendicular frames.
2. Creating Perpendicular Frames (Perp Frames vs. Contour?)
- I generate Perpendicular Frames (Perp Frames) along the middle axis.
- These frames define reference planes, which I need to generate points along the middle axis.
- The Contour component could be used here instead, but the difference is:
- Perp Frames create oriented planes along a curve, which is useful for controlling the wall’s cross-sections.
- Contour generates straight section cuts. I would probably need to find the mid point of each curve to continue with the script.
3. PCX (Curve | Plane Intersect)
- The PCX component (Curve | Plane Intersect) finds the intersection points between:
The side curve of the floor slab (from Step 1).
The Perpendicular Frames along the middle axis. - This creates a set of point running along the midde axis of the bridge.
4. PShift (Periodic Shift)
- PShift (Periodic Shift) moves items within a list in a cyclic manner.
- This helps reorder intersection points to ensure that curves later connect in a smooth flow.
- Without PShift, the curves generated in the next steps might become disjointed or misaligned.
5. Exploding the Data Tree
- The intersection points from PCX are stored in a nested structure, where each branch contains multiple points.
- Since I need to manipulate individual curves independently, I explode the tree to separate these elements.
- Instead of a single tree containing all points, the points are now broken into individual branches, allowing them to be used separately.
6. Using Arc SED (Arc with Start, End, and Direction)
Now that I have key points, I can start shaping the actual curves that will later define the walls.
- Arc SED (Start, End, Direction) generates an arc based on:
- A Start Point
- An End Point
- A Direction Vector that determines its bulge.
- By applying Arc SED to the intersection points, I create smoothly curved wall profiles instead of sharp, angular edges.
7. Scaling the Walls with Scale NU
- Scale NU allows the walls to be scaled parametrically, with a simple slider.
8. Length (LNG) & Range
- The Length (LNG) component measures the number of segments.
- The x-1 expression ensures that the curve division matches the actual number of segments, preventing errors
9. Graph Mapper
- Graph Mapper allows me to remap curve points using a graph-based function.
- Different graph types (Bezier, Gaussian, etc.) allow me to control how the wall curves change shape, giving me full flexibility over their appearance.
10. BND (Bounds) & ReMap
- BND (Bounds) finds the minimum and maximum values of the data.
- ReMap helps me limit the values into a custom range, which can then be controlled with a slider.
- In the final script, this slider controls how far the walls “climb” up the spine curves, created in this Step.
11. Merge the ReMapped Data Streams
- The function 1-x inverts values, so that the bridge can have walls on both sides.
- Grafting organizes the data structure into separate branches, ensuring that the different transformations apply independently to each segment.
12. Shatter
- Shatter splits curves into useful segments for the next steps.
- Reparametrizing normalizes curve domains to 0-1, making transformations more predictable.
- Grafting again ensures that the separate streams remain structured for the next step.
Possible Mistakes in This Step:
or at least mistakes that I made…

- PCX (Curve | Plane Intersect) generates multiple intersection points
- These points are structured as a data tree (organized lists of points, grouped by frame).
- BANG! is extracting data but still in tree structure
- {0;0;0;0} and {0;0;0;1} notation indicates that two separate branches are being extracted.
- However, the Arc component expects flat data, meaning it needs only one pair of start and end points per arc.
- PShift (Periodic Shift) reorders the list by shifting elements cyclically: The first point in each branch gets moved to the end, and everything shifts forward by one position. This makes sure that each point is paired correctly with the next one, creating a clean sequence of start and end points for the Arc component.

In the Arc SED → Scale NU setup, I forgot to add a Point component before connecting to Scale NU. Without it, the script does not know what to scale around, causing it to fail.
Step 4: Creating the Bridge Walls

Now that the curves defining the walls have been generated in Step 3B, the next step is to convert them into surfaces and finalize them as a mesh structure.
1. Creating the Bridge Wall Surfaces with Loft
Input: Curves from Step 3B
- The Loft component is used to create a continuous surface from the previously defined curves.
2. Panelizing the Walls Using TriB (Triangle Panels B) LunchBox plugin
- The TriB (Triangle Panels B) component is used to divide the walls into triangular panels.
- This step creates a modular system, making it easier to adjust panel size and arrangement.
3. Extracting and Manipulating Panel Center Points
- The Area component calculates the center of each panel, which serves as the anchor for transformations.
- The Pull component ensures that these points remain aligned with the original bridge structure, preventing distortions.
4. Controlling Panel Transformations with Graph Mapper & ReMap
- The panel center points are remapped using a Graph Mapper, allowing for custom scaling and shaping of the panels.
What’s the Role of BND (Bounds) and ReMap?
- BND (Bounds): Finds the minimum and maximum values of the panel positions.
- ReMap: Scales these values into a 0-1 range, making transformations predictable and proportional.
5. Finalizing the Walls: Mesh Extrusion
- The final panels are extruded to add thickness.
- The “Solid?” toggle allows switching between single-layer surfaces and fully closed mesh volumes.
Step 5: Creating the Railing

1. Defining the Placement of Vertical Handrail Supports
Dividing the Curve from Step 1 into Points
- These points act as the locations where the vertical handrail posts will be placed.
Why Use a Random Component?
- Instead of having perfectly uniform spacing, the Random component introduces slight variations to the division points.
- This makes the handrail more organic and less rigid-looking.
2. Generating the Vertical Handrail Posts
- The Move component is used to elevate the division points to the desired handrail height, controlled by the “Height of Handrail” slider.
- The original divided points and their moved ones are connected with the Line component to create the vertical rail posts.
- The Pipe component extrudes these vertical lines into cylindrical posts, giving them a defined thickness.
3. Creating the Handrail
- The InterpCrv (Interpolated Curve) component connects the top ends of the vertical posts, generating a smooth, continuous rail line.
- The handrail curve is then extruded into a solid pipe using another Pipe component.
- The pipe radius is controlled separately, allowing for a different thickness than the vertical posts.
4. Mirroring the Handrail for the Opposite Side
Short Animation
This short clip demonstrates some of the adjustments possible with the parametric bridge script, including modifications to curvature, wall height, panelization, and handrail size. However, the script offers a lot more: width adjustment, possibility to change the form of the walls as well as the size of their openings, and more.
How the Script Helped Find a Solution
The script provided a parametric solution to efficiently generate adaptive footbridges in a complex atrium where manual modeling would be time-consuming and inflexible. By using just three points to define the bridge, it automated the creation of the floor slab, walls, handrails, and timber panels, allowing for instant adjustments in width, curvature, height, and panelization. This eliminated the need for manual redesigns, making it possible to quickly adapt the bridges to different floor levels and varying atrium widths while maintaining design consistency and structural logic.
Where Are Its Limits?
The script has certain limitations that could impact its adaptability and real-world application. Structural analysis is not integrated, meaning the bridge’s form is optimized for design but lacks validation for load-bearing capacity, material strength, and deflection behavior. Without tools like Karamba3D, the bridge might require manual adjustments before fabrication.
Another constraint is texture mapping and material control, which currently require manual adjustments in Rhino. While the script generates precise geometry, UV mapping for realistic timber textures is not fully automated, making visualization less seamless.
Currently, the bridge wall heights are directly linked to the width of the floor slab, meaning wider bridges result in taller walls. The bridge walls could be separated from the floor slab width by setting a minimum human-scale height (e.g., 2.2m) and allowing independent control via a slider. This would ensure the walls remain comfortable for pedestrians
Future Improvements & Upgrades
Beyond My Studio Project
Although I developed this script specifically for my atrium bridges, it could be applied anywhere a quick, adaptable footbridge is needed. Whether it’s for urban design, landscape architecture, or even interior spaces, this approach makes bridge design faster, more flexible, and responsive to real-world constraints.
Karamba3D for Structural Analysis
- Right now, the script focuses on geometry generation, but it could be enhanced by incorporating Karamba3D to analyze load distribution, bending moments, and material efficiency.
- This would help determine optimal thickness, structure, and material use.
Playing Around with Bridge Walls
The bridge walls could be enhanced with kinetic openings, image-based patterns, or attractor-driven perforations to create a more dynamic and engaging experience. Kinetic panels could rotate, slide, or expand in response to movement, wind, or sunlight, making the bridge interactive and adaptable. Image-based openings could use a grayscale image to dictate perforation sizes, creating artistic facades or shading effects. Attractor-driven openings could vary in size based on key viewpoints in the building, naturally framing important views.
Plugin Used – LunchBox
I’d like to credit and thank Nathan Miller for the LunchBox plugin, which played a key role in simplifying the creation of the bridge wall panels and helped save time in the design process.
The plugin can be downloaded at: https://www.food4rhino.com/en/app/lunchbox