The Section Cut Tool got a big upgrade:
 

  • Ability to plot multiple load steps for a load case that contains multiple directions of loading.
    • Seismic X, Seismic X +e, etc.
    • Currently only supports ASCE 7-16 and ASCE 7-22 seismic loads. If you use this tool and want your specific code included. Leave a comment here or github. Should be a quick enough update.
  • Interactive plots with the data grid below (highlight a row in the datagrid and the corresponding plots will have a gold dot filled in).
  • Tabular data now outputs the length of the section cut.
  • Youtube video for install
    • Hearing yourself on a youtube video is just as bad as one might think it is, but hopefully this will help people get this up and running on their computers.
  • Youtube video for how to use the tool

The code has been updated on github and the install files have been uploaded as well. Give it a spin.

Coding

Coding this involved much more code than what I ever could have imagined. I should now by now that I should take my time estimates to achieve a task and multiply by about 5.

ETABs API - Database Tables, Not As Good As I Once Thought

Database tables seem to be the way the ETABs API is pushing coders to move to access data. This is good and bad from my beginners perspective. The good, most anything is available programatically. The bad, the API response is this garbled, unorganized mess of data. Take for example the section cut results.

I used to be able to call this function to retrieve section cut results before upgrading the tool to pull differing load steps.

This function was nice because it explicitly tells you what it will return. If you happen to throw in a load case with multiple load steps into this function, it will not work for some reason? I was able to get around this by calling the database tables method to return the section cut database table.

            string TableKey3 = "Section Cut Forces - Analysis";
            string[] FieldKeyList = null;
            string GroupName = "All";
            int TableVersion = 1;
            string[] FieldKeysIncluded2 = null;
            int NumRecords = 0;
            string[] TableData2 = null;

            _SapModel.DatabaseTables.GetTableForDisplayArray(TableKey3, ref FieldKeyList, GroupName, ref TableVersion, ref FieldKeysIncluded2, ref NumRecords, ref TableData2);
            //THIS IS THE LIST TO HOLD ALL LOAD STEP RESULTS FOR A SELECTED LOAD CASE WITH STEPS
            listSectionResults = new List<SectionResults>();

            //this is the multiple load steps
            if (FieldKeysIncluded2.Contains("StepNumber"))
            {
                //This list will contain all of the results from one load case with multiplesteps                
                
                List<int> indices = new List<int>();
                // Find indices of "EqAll" in TableData2
                int loadSteps = listBoxLoadSteps.Items.Count;
                indices = SectionCutResults.FindIndices(TableData2, LoadCaseComBox.SelectedItem.ToString());

                //int step = indices.Count() / loadSteps;
                // Grab specific items by index using LINQ
                var specificItems = indices.Where((item, index2) => index2 % loadSteps == 0);
                List<string> OrderedSeismicList = new List<string>();
                OrderedSeismicList = LoadCaseList[index].GetOrderedSeismicDirections();

                //run from 0 to load steps
                for (int i  = 0; i < loadSteps; i++)
                {
                    List<Double> F1loop = new List<double>();
                    List<Double> F2loop = new List<double>();
                    List<Double> F3loop = new List<double>();
                    List<Double> M1loop = new List<double>();
                    List<Double> M2loop = new List<double>();
                    List<Double> M3loop = new List<double>();
                    //IF THIS TABLE GETS REWORKED IN THE FUTURE, THIS WILL NEED TO BE RECODED!!!
                    SectionResults loadCaseResults = new SectionResults();
                    //AREA OF INTEREST

                    //note index is the corresponding loadcase selected in the LoadCaseList
                    //This is Eq X, Eq X e+ etc.
                    loadCaseResults.LoadDirection = OrderedSeismicList[i];
                    //We generatate all of the results for an individual load case, load step in this loop here.
                    foreach (int sectionResult in specificItems)
                    {
                        F1loop.Add(Convert.ToDouble(TableData2[sectionResult + i * 14 + 4]));
                        F2loop.Add(Convert.ToDouble(TableData2[sectionResult + i * 14 + 5]));
                        F3loop.Add(Convert.ToDouble(TableData2[sectionResult + i * 14 + 6]));
                        M1loop.Add(Convert.ToDouble(TableData2[sectionResult + i * 14 + 7]));
                        M2loop.Add(Convert.ToDouble(TableData2[sectionResult + i * 14 + 8]));
                        M3loop.Add(Convert.ToDouble(TableData2[sectionResult + i * 14 + 9]));
                    }
                    loadCaseResults.F1 = F1loop.ToArray();
                    loadCaseResults.F2 = F2loop.ToArray();
                    loadCaseResults.F3 = F3loop.ToArray();
                    loadCaseResults.M1 = M1loop.ToArray();
                    loadCaseResults.M2 = M2loop.ToArray();
                    loadCaseResults.M3 = M3loop.ToArray();
                    listSectionResults.Add(loadCaseResults);
                }
            }

The problem with this? All the data that is returned is in this massive list/array. I had to write a lot of code to pick apart this massive response, a big bummer from the super clean AnalysisResults.SectionCutAnalysis method used before.

Pro tip, use the view command in visual studio for a variable explorer! So sad I did not know about this until about a week ago. A huge time saver!

The same issue arose with trying to find out what sort of seismic load cases had been generated. The ETABs API developers seem to have made a cognizant decision to move away from specific methods and move towards the database table responses for grabbing all data.

There used to be an autoseismic interface that appeared to work back in the day

but now, these functions do not return anything meaningful. I had to go to database tables to retrieve this info, more unorganized data to sift through and organize myself.

 if (CodeName == "ASCE 7-16")
 {
     string myTableKey = "Load Pattern Definitions - Auto Seismic - ASCE 7-16";
     string[] FieldKeyList = null;
     string GroupName = "";
     int TableVersion = 0;
     string[] FieldsKeysIncluded = null;
     int NumberRecords = 0;
     string[] TableData = null;
     _SapModel.DatabaseTables.GetTableForDisplayArray(myTableKey, ref FieldKeyList, GroupName, ref TableVersion, ref FieldsKeysIncluded, ref NumberRecords, ref TableData);

Another pain point, why do the database tables for auto seismic not correspond to the section cut force analysis tables??? More coding required to dig through all this.

Lastly on the coding side, the plots are now interactive if you click on the row in the datagrid.

The interactive plots with highlighting gold selected rows was achieved through this item in live charts called "mappers". After much coding and interactions with chatgpt, I was able to get a mapper to work with the omitted selected row in the datagrid.

In addition, I attempted to add some code to check if the analysis had already run and skip the tedious rerun if required. I was able to use this function, _SapModel.Analyze.GetCaseStatus(ref NumberItems, ref CaseName, ref status);

to check if the load case had run. Unfortunately though, the section cut definition table is not available if the model is locked and I have a question into CSI regarding this. It seems like you should be able to add section cuts while the model is locked. More on this here.

Uses with the tool

Now that the tool can plot diaphragm shears for code mandated mass eccentricities, I want to run some sample cases to test some of my old design philosophies, for example, due to computational time constraints, I would often design my diaphragm shear DCRs to be a max of 90% to account for the +e/-e mass eccentricities. From my quick tests, this may not have been as conservative as I thought it was.

 

ETABs C Sharp

Our Sidebar

You can put any information here you'd like.

  • Latest Comments
  • retug on ETABs API - More Examples (Database Tables) -

    Hi rajavardhan, are you not able to delete selected frames and walls based on section properties through the ETABs program itself? Or through the API? I could put together a few quick examples for you with the API if needed.

  • rajavardhan on ETABs API - More Examples (Database Tables) -

    Hi, I am not able to select frames and walls based on section properties in etabs v21 and then delete selected frames and walls..can anyone suggest me the code to do it use Excel VBA code 

  • retug on SAP2000 API Example -

    Thanks James, appreciate you taking a look at the blog.

    The stuff you have been making is really cool too, always happy to see more people making coding more approachable for the practicing structural engineer.

    The package you linked for SAP2000 looks good, I will have to check it out.