Some pointless fun with C# and the Grasshopper timer

I made a thing, and it ripples!

It could be sound in an auditorium. It could be waves in water. It could be energy dissipating from an earthquake’s epicentre. But that’s not the point.

What it is is a great demonstration on what you can make with the Grasshopper timer, and bit of C#, and 15 minutes to kill.

In the C# component, there are two regions you can edit: the RunScript section, and the ‘additional code’ section. Data stored in RunScript is volatile – it gets deleted every time the component is run. But data stored in the second region is preserved.

By running a timer on our component, it will be executed repeatedly. We can use this second region to hold information between these executions, allowing us to build up complex and dynamic behaviour in Grasshopper.

Grasshopper component C# timer example

The code within the C# component handles each ‘frame’ of the animation. It maintains the current time (increasing by 1 for each cycle) and uses this time to decide what colour each part of the mesh will be.

  private void RunScript(bool _clap, bool _reset, Mesh _mesh, ref object A)
  {
    
    thetime++;

    //button actions
    if(_clap)
    {
      times.Add(thetime);
    }
    if(_reset)
    {
      times.Clear();
      thetime = 0;
      CalcDistances(_mesh, new Point3d(0, 0, 0));
    }

    //maintain list size to maintain performance
    if(times.Count > 50) times.RemoveAt(0);

    //calculate mesh colours
    _mesh.VertexColors.Clear();
    int i = 0;
    foreach(var v in _mesh.Vertices)
    {
      bool shouldbegreen = false;
      foreach(var time in times)
      {
        if(thetime == (time + (int) (distances[i])))
        {
          shouldbegreen = true;
        }
      }
      if(shouldbegreen)
      {
        _mesh.VertexColors.Add(Color.Green);
        _mesh.Vertices.SetVertex(i, _mesh.Vertices[i].X, _mesh.Vertices[i].Y, 1);
      }
      else
      {
        _mesh.VertexColors.Add(Color.Red);
        _mesh.Vertices.SetVertex(i, _mesh.Vertices[i].X, _mesh.Vertices[i].Y, 0);
      }
      i++;
    }

    //output
    A = _mesh;
  }

  // <Custom additional code> 

  int thetime = 0;
  List<int> times = new List<int>();
  List<double> distances = new List<double>();
  
  //preprocessed here to speed up calculation
  public void CalcDistances(Mesh msh, Point3d pt)
  {
    distances.Clear();
    foreach (var v in msh.Vertices)
    {
      distances.Add(pt.DistanceTo(v));
    }
  }

A simple timer example for the Grasshopper C# component

grasshopper-timer

Create a simple timer in Grasshopper using the built-in C# component with this example script.

What this does

Set runtimer to true. The component will build a list of the current time and date, once per second.

When runtimer is set to false, the timer is turned off and the list is displayed.

Code

  private void RunScript(bool runtimer, bool reset, ref object A)
  {
    if(runtimer) Example.TurnOnTimer();
    if(!runtimer) Example.TurnOffTimer();
    A = rtnlist;
  }

  // <Custom additional code> 

  public static List<string> rtnlist = new List<string>();

  public class Example
  {
    public static System.Timers.Timer aTimer = new System.Timers.Timer(1000);

    public static void TurnOnTimer()
    {
      rtnlist.Clear();
      aTimer.Elapsed += OnTimedEvent;
      aTimer.Enabled = true;
    }

    public static void TurnOffTimer()
    {
      aTimer.Elapsed -= OnTimedEvent;
      aTimer.Enabled = false;
    }

    private static void OnTimedEvent(Object source, System.Timers.ElapsedEventArgs e)
    {
      rtnlist.Add(e.SignalTime.ToString());
    }
  }

Download

You can download the above code as a Grasshopper user object here


Further information

MSDN guide: timers in C#

Grasshopper timer using Python

If you are looking to add a timer to a Python component without using the timer component, have a look at Anders Deleuran’s code here.