Import, Format and Plot Stress/Strain Data

In this tutorial we will import the comma separated value (*.cvs) spread sheets produced by the Instron tensile testing machine, namely force and elongation, and we will convert and plot a stress/strain graph in Rhino.

uts

Technique

Performing the aforementioned tasks will (re)introduce the following key techniques which are more broadly applicable to various other operations:

  1. The standard operating procedure of importing/exporting data from Grasshopper.
  2. Reading text files from the local machine (obtaining files in a folder and reading all text)
  3. Parsing text information to extract numerical values (csv lines to point coordinates)
  4. Linear mapping of signals (force/elongation to stress/strain)
  5. Computing the maximum value of a series (to find the ultimate tensile strength)
  6. Creating annotations and exporting them into Grasshopper
  7. Placing geometry into Rhino’s active document (custom backing into layers)

uts2

Procedure

 private void RunScript(List<string> Files, 
   ref object Geometry, ref object AnnoTxts, ref object AnnoPnts)
 {
    var BAKE_GEOMETRY = false;

    var geometry = new List<object>();
    var annopnts = new List<object>();
    var annotxts = new List<object>();

    //-- Length of Specimen (mm)
    //--
    double length = 300.0;

    //-- Cross-Sectional Area (sqmm)
    //--
    double area = 9.0 * 100.0;

    //-- Folder with All Data
    //--
    foreach( var file in Files )
    {
      //-- Ultimate Tensile Strength
      //-- Value and Position
      //--
      double uts = 0.0;
      double uts_x = 0.0;
      double uts_y = 0.0;

      //-- Load File Contents into a List of Text Lines
      //--
      var lines = File.ReadAllLines(file);

      //-- Polyline to Store Points
      //--
      var poly = new Polyline();

      //-- Skip First Two Lines (Headers)
      for( var index = 2; index < lines.Length; index++ )
      {
        //-- Split a Text Line by Commas into Tokens
        //--
        var line = lines[index].Split(new char[]{','},
          StringSplitOptions.RemoveEmptyEntries);

        //-- Convert Text to Real Numbers
        //--
        double L; if( !double.TryParse(line[0], out L)) L = 0.0;
        double E; if( !double.TryParse(line[1], out E)) E = 0.0;
        double T; if( !double.TryParse(line[2], out T)) T = 0.0;

        //-- Convert Extension to Strain and Load to Stress
        //-- Units check out? Check Wolfram Alpha
        //--
        double strain = E / length;
        double stress = L / area;

        //-- Scale data to nice proportions
        //-- Strain: 100% and Stress: MPa
        //--
        double x = strain * 100;
        double y = stress;

        //-- Store Point
        //--
        poly.Add(x, y, 0);

        //-- Check if UTS
        //--
        if( stress > uts )
        {
          uts = stress;
          uts_x = x;
          uts_y = y;
        }
      }

      //-- Add Annotation
      //--
      var name = Path.GetFileNameWithoutExtension(file);
      var text = string.Format("ID:{0}\r\nUTS:{1:0.000}MPa", name, uts);
      var node = new Point3d(uts_x, uts_y, 0);

      annotxts.Add(text);
      annopnts.Add(node);

      Print("ID:{0} UTS:{1:0.00}MPa", name, uts);

      //-- Custom Baking
      //--
      //!! BE CAREFULL THIS MAY CRASH RHINO
      if(BAKE_GEOMETRY)
      {
        var layer_index = Rhino.RhinoDoc.ActiveDoc.Layers.Find(name, true);
        if( layer_index < 0 )
        {
          //-- Create Layer if Doesn't Exist
          //--
          layer_index = Rhino.RhinoDoc.ActiveDoc.Layers.Add(name, Color.Red);
        }
        var layer = Rhino.RhinoDoc.ActiveDoc.Layers[layer_index];

        var attributes = new Rhino.DocObjects.ObjectAttributes();
        attributes.LayerIndex = layer_index;

        Rhino.RhinoDoc.ActiveDoc.Objects.AddPolyline(poly, attributes);
        Rhino.RhinoDoc.ActiveDoc.Objects.AddText(
          text, new Plane(node, Vector3d.ZAxis),
          0.05, "Arial", false, false, TextJustification.MiddleCenter, attributes);
      }

      //-- Store Graph
      //--
      geometry.Add(poly);
    }

    //-- Emit Geometry
    //--
    Geometry = geometry;
    AnnoPnts = annopnts;
    AnnoTxts = annotxts;
}