Using Python To Analyze Isometric Force Time.7
Using Python To Analyze Isometric Force Time.7
Isometric Force-Time
Curves
Jason Chadwick Smith,1 Tsuyoshi Nagatani,2 Stuart N. Guppy,2 and Guy Gregory Haff2,3
1
Department of Kinesiology, Coastal Carolina University, Conway, South Carolina; 2Strength and Power Research
Group, School of Medical and Health Sciences, Edith Cowan University, Joondalup Western Australia; and 3Sport,
Exercise, and Physiotherapy, University of Salford, Greater Manchester, United Kingdom
Supplemental digital content is available for this article. Direct URL citations appear in the printed text and are provided
in the HTML and PDF versions of this article on the journal’s Web site (http://journals.lww.com/nsca-scj).
ABSTRACT vided can be used to analyze the IMTP midthigh pull (IMTP) and isometric
force-time curve data, it can be modi- squat, should be used in addition to
The isometric midthigh pull (IMTP) is
fied to examine other metrics as these tests to provide a greater diag-
a commonly used strength diagnostic
needed by the user (see, Supplemen- nostic picture of the athlete’s force-
tool that can give insight into an ath-
tal Digital Content 1, http://links.lww. generating capacities (19). Incorporat-
lete’s force-generating capacities. The
com/SCJ/A412). ing these types of tests into the moni-
resulting force-time curves generated
toring plan allows for the creation of
are commonly analyzed using com-
force-time curves that can be system-
mercial software packages that pro- INTRODUCTION
atically analyzed to provide detailed
vide a variety of metrics. Although t is well documented that maximal
these software packages are useful,
they are often costly and operate as
a “black box,” limiting the control over
I strength, which represents the abil-
ity to exert external force on an
object or resistance, is an important
information about various aspects of
the athlete’s force-generating capaci-
ties (5,6,30).
how these metrics are calculated. A factor underpinning the performance One of the most common multi-joint
template created in Excel can be used of many athletic tasks, enhances isometric tests is the IMTP, introduced
to analyze isometric data. However, fatigue resistance, and reduces injury in the scientific literature in 1997 as
creating a custom script to analyze risk (7,14,22,28,31). Because of its over- a method for quantifying the athlete’s
isometric trials can be more time- all importance, it is widely accepted maximal force-generating capacity and
that the maximization of muscular the rate at which force can be applied
efficient. To provide users with an
strength is a central training target during maximal contractions (16,17).
alternative analysis option, this article
when working with athletes. To facili- Over time, the force-time curves gen-
provides a guide for selecting IMTP
tate the development and monitoring erated from this test have been further
force-time curves and variables for
of maximal strength, various testing dissected to include analyses of the
analysis and how to use Python to
and monitoring methods have been forces at specific epochs, changes in
perform these analyses. Basic proce- proposed. The most common method force, and incorporating analyses of
dures are provided to ensure that for assessing maximal strength is to impulse (9,16). Although the original
accurate force-time curves are assess the athlete’s 1 repetition maxi- incarnation of the test used a single
selected and analyzed, followed by mum or repetition maximum during force plate, more recently, it has
strategies for using Python to read a specific resistance training exercise become commonplace to use 2 force
files, filter data, calculate force-time (4,14). Although these tests are useful plates so that individual limb force-
curve variables, graphically present for guiding the training process, they time characteristics can be evaluated
data, and write results to a report are do not provide detailed information
discussed. Although the script pro- about how the athlete generates force. KEY WORDS:
To address this shortcoming, research- Performance testing; kinetics; sports
Address correspondence to J. Chadwick ers have proposed that multi-joint iso- science; force platform
Smith, [email protected]. metric testing, such as the isometric
Copyright © National Strength and Conditioning Association. Unauthorized reproduction of this article is prohibited.
Python & Isometric Force-Time Curves
to identify lower limb force generation reported to have an increased potential strapped to the bar to determine if pre-
asymmetries. The inclusion of these for processing errors and disagree- tension is being applied to the bar
measures as part of the force-time ments across analyses depending on (Figure 4C), as this can interfere with
curve analysis likely increases the abil- the software package used (24). This the onset detection and influence the
ity of the test to be used as a diagnostic has led many sport scientists and reliability and accuracy of the collected
tool, especially when considering strength and conditioning professio- measures (5,6). The final check deter-
sporting tasks such as jumping, sprint- nals to seek alternative ways of creating mines if the current trial is within 250 N
ing, and change of direction are time- their bespoke force-time curve analysis of the last trial collected in the testing
constrained (6) and asymmetries are software with programs such as Excel session. If the trial is within 250 N of
often related to injury risk (2,18). (5), R (24), or Python (29). With the last trial, then the trial can be
Generally, the peak forces, maximal increasing interest in using open- accepted (21). Although this method
forces determined at specific time access computer languages, such as of quality control is commonly used,
points, and impulse measures have Python, to analyze force-time curves, it may not be ideal for smaller or weak-
been reported to be highly reliable Smith (29) recently presented a user- er individuals, such as children (25). As
friendly guide on using this program- such, it may be warranted to use a per-
within and between training sessions
ming language to batch analyze verti- centage difference-based threshold for
(11,12,16). Conversely, the rate of force
cal jump force-time curves. Given determining if additional trials are war-
development (RFD) has not consis-
force-time curve data are fundamen- ranted. Based on the limited available
tently been reported to be reliable
tally similar in structure regardless of research exploring percentage differ-
either within or between sessions,
the test performed, Python may pro- ence thresholds, if the current trial
regardless of whether peak RFD
vide an alternative solution for analyz- is ,15% different than the last trial,
(pRFD) or time point specific RFDs
ing IMTP force-time curves. the trial should be accepted (25). If
are analyzed (13,16). It is important
Therefore, the purpose of this article is the trial fails to meet these criteria, it
to note that the reliability of the mea-
to discuss the key metrics that need to should be discarded, and additional tri-
sure can be impacted by not only the
be considered when analyzing force- als should be conducted (Figure 2).
methodology of testing but the choices
made when analyzing the force-time time curves collected from IMTP trials, If the testing trials meet all these crite-
curve (10,13). Specifically, manual compare using Excel and Python to ria, they can be analyzed for the com-
force-onset identification methods analyze force-time curves, and demon- mon force-time curve variables.
result in different levels of reliability strate how to write Python code so that
when compared with the automated manual or automated force-time curve COMMON FORCE-TIME CURVE
(40 N, 5 SDs, and 3 SDs) onset selec- analyses can be performed. VARIABLES
tion methods used by some practi- After completing an IMTP test, the
tioners and researchers. Although CHOOSING ISOMETRIC MIDTHIGH force-time curve generated can be ana-
manual force-onset identification is PULL TRIALS FOR ANALYSIS lyzed to determine an athlete’s maxi-
considered the criterion method for as- A visual inspection of the IMTP force- mal and explosive strength levels (14).
sessing force-time curves, it requires time curve should be made in real time During this analysis, the most common
custom software, such as LabView to determine if the collected trial is force measurements calculated include
(National Instruments, Austin, TX), acceptable and if additional trials the peak force and forces determined at
that can be associated with a significant should be collected (5,6). A trial is predetermined time periods (Table 1).
financial cost (10). deemed unacceptable if there is not Generally, when the IMTP is performed
In addition, manual force-time curve a stable weighing period, there is a clear with standardized and systematic meth-
analyses can result in a significant time countermovement .50 N that occurs ods, the peak force is highly reliable (6,14)
burden delaying data reporting. An before the initiation of the pull, or there and reflects the athlete’s maximal force-
alternative approach is to use real- is obvious pretension (Figure 1A), as generating capacities. Generally, the peak
time automated analyses using com- this will interfere with the ability to force determined during the IMTP test
mercially available software packages. accurately identify the initiation of has been reported to be significantly cor-
These software packages have become the pull (5,6,27) or if the peak force related (r 5 0.740 to 0.980) with the max-
commonplace within the industry as occurs at the end of the trial imal weight lifted in competitive
they allow the practitioner to rapidly (Figure 1B). If the trial does not contain weightlifting movements (i.e., snatch
collect and analyze force-time curves any of these conditions, it is deemed and clean and jerk) and their derivatives
collected during the IMTP (24). acceptable (Figure 1C). (15,20,30) and other strength-based exer-
Although these software packages are In addition, it is important to carefully cises such as the back squat (36), deadlift
often easy to use, they come with a sig- inspect the forces applied during the (8), and bench press (23). In addition, the
nificant financial cost (1,000 to 3,000 standing quiet period where the ath- IMTP peak force has been significantly
USD per year) and have recently been lete is in the ready position and correlated to sprint performance
289
Strength and Conditioning Journal | www.nsca-scj.com
Copyright © National Strength and Conditioning Association. Unauthorized reproduction of this article is prohibited.
Python & Isometric Force-Time Curves
license, additional toolboxes may need learning Python, we have used it to cre- exported as CSV files for further anal-
to be purchased if advanced computa- ate this guide for analyzing IMTP data ysis. During the first second of data
tions are required. Alternatively, R, from multiple trials. collection, the participant performed
a commonly used open-access statistical a quiet stance. Then, data collection
The script presented in Supplemental
analysis platform, can create a script to was paused to strap the participant to
Digital Content 1 (see, http://links.
analyze IMTP data without additional the bar. Finally, data collection was
lww.com/SCJ/A412) can be modified
cost. However, the syntax used by R resumed to allow the participant to
makes learning this programming plat- to suit the user’s needs and data. A complete the IMTP trial. All trials were
form more difficult than learning MAT- series of IMTP trials were collected saved to a single CSV file (see Supple-
LAB commands for a new user. Python with the use of an isometric rack (Vald, mental Digital Content 2, http://links.
is another open-source, general pro- Queensland, Australia) and a pair of lww.com/SCJ/A413). Each trial com-
gramming language for various applica- Pasco Force Plates (PS-2141, PASCO prised 4 columns of data (time, Fz for
tions, such as web development, data Scientific, CA) that sampled at left leg, Fz for right leg, and combined
visualization, and scientific computing. 1,000 Hz and Pasco Capstone Software Fz, with Fz representing vertical
Because of the lack of cost and ease of (V2.4.0) that allowed data to be ground reaction forces).
291
Strength and Conditioning Journal | www.nsca-scj.com
Copyright © National Strength and Conditioning Association. Unauthorized reproduction of this article is prohibited.
Python & Isometric Force-Time Curves
PYTHON AND INTEGRATED 13 of the script accomplish this task. To function to create a list of trial names
DEVELOPMENT ENVIRONMENT be more efficient, we referenced the based upon the number of trials (e.g.,
(IDE) INSTALLATION AND package or specific module using an Trial 1, Trial 2) and then assign it to
CONFIGURATION
abbreviation. For example, pandas a new variable called “trial_choices.”
Before creating a Python script or pro- was referenced as “pd.” Therefore, we
gram, the user must install Python Lines 32–38 were used to set up the
called the pandas library in our script user interface for trial selection using
(http://python.org) and an editor or using “pd” instead of typing “pandas.”
integrated development environment PySimpleGui, which includes a mes-
A summary of each of the packages, sage “Select a Trial,” a combo box to
(IDE) on their computer. To create the libraries, and modules imported into
script for this paper, we used one of the select a particular trial from dataframe
our script and a brief explanation for “df,” and a button labeled “Analyze.”
most popular IDEs, PyCharm (http:// each package is provided in Table 2.
jetbrains.com/pycharm). There are 2 Line 38 creates a popup window using
versions of PyCharm, 1 for research PySimpleGui with its title labeled
FILE AND TRIAL SELECTION “Select Trial” based upon layout
and 1 for the community. Because the After installing the necessary Python
community version was free, we used it defined earlier and assigns it to a new
packages, we determined a visual style variable called “window.” Lines 40–54
to create this guide. Smith (29) provided for a popup window by executing Line
a supplemental digital video (http:// use a while True loop function, which
16, as the popup window was used for continues to run until a “break” state-
links.lww.com/SCJ/A390) that shows the user to select a CSV file and a spe-
the user how to install Python and Py- ment is encountered. Line 41 reads an
cific trial from it. Line 17 in the script event and associated variables from the
Charm, and another supplemental digital creates a small window using PySim-
video showing the user how to properly popup window created earlier. Line 43
pleGui, where the title of the window checked if the event is the window
configure PyCharm (http://links.lww. is labeled “File Selector” and the mes-
com/SCJ/A391). being closed. If this was true, line 44
sage “Select a CSV file” appears inside then used the “break” statement to ter-
the window. After selecting the file, the minate the infinite loop. Line 45
IMPORT PYTHON PACKAGES user presses the “Ok” button, and the checked if the event is the “Analyze”
After the user has installed Python and window closes. button being clicked. If this was true,
properly configured their IDE, they We have stored the selected CSV file the script proceeded to lines 46–54.
can start writing their script. When path in the “csv_file” variable. To select Line 46 used the selected trial name
writing the script, it can be helpful to which trial to analyze from the selected to retrieve a particular trial from the
make comments within the script to CSV file, we must first convert it into combo box and find its index within
help the user understand different sec- a pandas dataframe. Lines 19–25 con- “trial_choices,” which is assigned to
tions. In Python, you can use the verted the selected CSV file into a pan- a variable called “selected_trial_index.”
pound or hashtag (#) symbol to make das dataframe “df.” If a CSV file was not This variable was used in combination
these comments. When running the selected or malformed (e.g., a text file with “num_columns_per_trial” to cal-
script, any line that begins with the was selected), the error message “Error culate the start and end columns in the
pound symbol is ignored by Python. reading CSV file” is displayed to inform dataframe “df” in lines 47–48. Line 49
We have used comments to break the user about the error. If there was no used pandas “.iloc” method to extract
our script into several sections to help error during the CSV file reading pro- the data for the selected trial from the
the reader understand each section of cess, we proceed to next lines of code, datafame “df.” This line of code
the Python script. where line 27 sets a new variable called selected all rows using “:” and a specific
Most Python scripts will start with “num_columns_per_trial” to 4. This range of columns determined by the
installing the necessary Python pack- suggests that 4 columns correspond start and end columns defined earlier
ages and importing them into the to each trial in the dataframe “df.” If to create a new dataframe “data.” Lines
script. This can be done directly from there are only 2 columns correspond- 50–51 were used to print information
PyCharm’s Python Packages window ing to each trial in the dataframe “df” about the selected trial and the corre-
(see Smith (29) Supplemental Digital (e.g., only using a single force plate), 2 sponding data for that trial, which pro-
Content 9, http://links.lww.com/ should be assigned to this variable vided feedback to the user about the
SCJ/A391). Several packages are instead of 4 to represent the time and analysis being performed. Line 52 used
needed for the Python script created force columns. Line 28 calculates the the “break” statement to break out of
based on this paper. For some of these number of trials in the dataframe “df” the while True loop after trial selection
packages, we will only be using specific by dividing the total number of col- was completed. Once the dataframe
modules. We did not need to import umns by the number of columns per “data” was created, line 56 was used
the entire package and have specified trial to create a new variable called to assign new column names to this
the modules to be imported. Lines 1– “num_trials.” Line 29 uses a for loop dataframe, specifically “Time,” “rFz,”
“lFz,” and “Fz.” If the user has a single “Fz.” To visually verify that raw data a graph for the user to inspect. The user
force plate, line 56 would be modified for IMTP data were successfully im- should be able to view a force-time
to name the 2 columns “Time” and ported, lines 59–60 were used to create curve on the graph (see Video 1).
293
Strength and Conditioning Journal | www.nsca-scj.com
Copyright © National Strength and Conditioning Association. Unauthorized reproduction of this article is prohibited.
Python & Isometric Force-Time Curves
INSPECTING THE FORCE-TIME start. Line 63 in the script creates of data collection. Line 72 uses the
CURVE AND WEIGHT a popup window for the user to enter “std” function to calculate the SD of
DETERMINATION the time to start the weight determina- the individual’s weight. We labeled this
After the appropriate trial has been tion. From PySimpleGui, we can use variable “stddev”. Line 73 creates a vari-
selected, we need to inspect the the “popup_get_text” method to dis- able called “SD3,” representing 3 SDs
force-time curve to ensure no counter- play a small window. The title of the of the “Weight” variable. Lines 74 and
movement (i.e., .50 N) was performed window was labeled “Weight Determi- 75 calculate the values associated with
at the beginning of the trial. In addition, nation” and the message “Enter time in 3 SDs above the mean (“WSD_pos3”)
we need to determine the participant’s ms to begin weight determination” was and 3 SDs below the mean
weight. This was done to determine placed inside the window. Although (“WSD_neg3”).
the net force, and our force variables this is a text window, the user should
could be expressed relative to body Lines 78–84 were used to notify the
only input an integer in the window. user if a countermovement was de-
mass later in the script. Graphing the After doing so, the user presses the
force-time curve allows the user to tected before the beginning of the trial.
“Ok” button, and the window closes. The script will look through the Fz
visually inspect the data to determine The value entered by the user is then
if a countermovement was performed data to see if any value is 50 N below
labeled as “trim.” Lines 64–67 use an the variable Weight. Because we do not
at the beginning of the trial and find the “if-else” statement to determine the
flattest portion of the force-time curve, want to include Fz data at the end of
value of “trim.” If the user does not the trial, we need to trim our Fz and
which is used for their weight. enter anything into the popup window, time data. Line 78 uses the “idxmax”
Lines 59 and 60 were used to create lines 64 and 65 tell the script to set the function to find the location of the peak
and display the graph. Line 59 uses trim value equal to zero. This means Fz value in our dataframe. Line 79 uses
“plt.plot” to generate a plot using time that the script will use the beginning the “truncate” method to create a copy
from the “data” dataframe for the x-axis of the data file as the starting point for of the dataframe, df, and remove all
and “Fz” from the “data” dataframe for the weight determination. If the user data after the peak Fz value. This
the y-axis. Line 60 uses the “plt.show” enters a value into the popup window, new dataframe is labeled “df1.” Line
function to display the graph in a sep- the script presented in lines 66 and 67 80 calculates the threshold for detect-
arate window. If needed, the user can converts that value to an integer and ing the countermovement by subtract-
click on the magnifying glass in the calls it “trim.” ing 50 N from the variable Weight.
upper right-hand portion of the win- Line 69 creates a new dataframe called This threshold is labeled as “a.” Lines
dow to zoom in by clicking and drag- “df,” which will be a copy of the “data” 81–84 use an if-else statement to deter-
ging the mouse over the portion of the dataframe that has removed all the mine if the threshold was achieved or
graph where they want to zoom in. data before the value labeled as “trim.” not. Line 81 uses the “any.()” method
The home button (the icon that looks Line 70 calculates the weight by taking to determine if any Fz value in the df1
like a house) can restore the graph to the mean of the first 1,000 data points dataframe is 50 N less than the variable
its original view. After inspecting the of the “Fz” data in the “df” dataframe. Weight. If an Fz value meets this crite-
graph, the user can close the graph This weight variable was labeled as rion, line 82 displays a popup window
by clicking on the “X” in the top “Weight.” Later in the script, this vari- to notify the user that a countermove-
right-hand corner. able is used to calculate net force. Line ment was detected. If no countermove-
For weight determination, 1 full sec- 71 calculates the participant’s mass by ment is detected, line 84 displays
ond of data must be collected while dividing the “Weight” by the absolute a popup window to provide the user
the participant stands quietly without value for gravity (9.81). This mass vari- with the message, “No countermove-
grasping or being strapped to the bar. able is then labeled as “Mass.” Later in ment detected.”
In our setup, we collected the first sec- the script, this variable was used to Lines 87–95 can be used if the user
ond of data while the participant was express the force variables relative to wishes to automate the process of se-
not grasping or strapped to the bar, body mass and allometrically scaling lecting the beginning of the trial
paused data collection to allow them these force variables. instead of using the previously
to secure their lifting straps and grasp Before determining the onset of IMTP, described manual selection method.
bar, and resumed data collection for we should ensure that no excessive Video 1 shows how to use the script
the trial. Because the data were col- movement was being performed with the manual trial start selection
lected at 1,000 Hz, we will need at before the start of the trial. To aid the method and with this automated
least 1,000 data points before the user in this task, we will have the script method. Because these lines begin with
beginning of the movement. After draw horizontal lines on the force- the pound symbol, Python will skip
visually inspecting the graph, the user time curve that correspond to 3 SDs over them to get to line 98, which be-
should be able to identify the time above and below the mean weight of gins the manual selection at the start of
point where this calculation should the first second (i.e., 1,000 data points) the trial. Therefore, if the user wishes to
295
Strength and Conditioning Journal | www.nsca-scj.com
Copyright © National Strength and Conditioning Association. Unauthorized reproduction of this article is prohibited.
Python & Isometric Force-Time Curves
set to “pick_event,” which means that “df2” dataframe. Line 145 tells the calculated at 1,000 Hz, each row rep-
when the user interacts with a plot by script to subtract the “Time” associated resents the time of 1 ms. Therefore, we
clicking on a data point within the plot, with the start of the trial from each row used “df2.Fz.iloc[50]” to determine the
the “pick_event” is triggered. When in the “Time” column. The “iloc[0]” gross peak force at 50 ms. The same
this occurs, the “onpick” function refers to the first value associated with function was applied for each epoch,
defined earlier is executed. Line 126 the “Time” column of the “df2” thus creating the variables gF50,
was used to set the title of the plot, dataframe. gF100, gF150, gF200, and gF250,
and the text defined in line 127 (onset which represented the gross peak force
time) was displayed above the under- at 50, 100, 150, 200, and 250 ms,
line “______” in the plot. Lines 128– CALCULATING METRICS
respectively. Similarly, the “iloc[]”
129 were used to label the x-axis and Now that we have a working data-
function was applied to the “net_-
y-axis of the plot as “Time” and “Fz,” frame containing only the IMTP data,
Force” column of the “df2” dataframe
respectively. Line 131 was used to dis- we can calculate the various force-time
to calculate the net force at each epoch.
play the plot, where the user can click curve metrics. Line 148 used the
The net force at 50, 100, 150, 200, and
on a data point to execute line 124. In “apply” and “lambda” functions to cre-
250 ms were labeled “F50,” “F100,”
case the user wishes to know what the ate a new column, called “net_Force,”
“F150,” “F200,” and “F250,” respec-
force value (Fz) was at the onset time, within the dataframe called “df2.” This
tively. The relative net force at each
lines 128–129 were used to print infor- new variable was calculated by sub-
epoch was calculated by dividing
mation about this. tracting “Weight” from each row in
“F50,” “F100,” “F150,” “F200,” and
the “Fz” column. Line 149 determined
“F250” by the individual’s mass
the peak net force in this dataframe.
TRIMMING THE FORCE-TIME (“Mass”). These relative net forces
CURVE This variable is given the label “Peak_-
Force.” Because the data in this data- were labeled “relF50,” “relF100,”
After we have identified the beginning “relF150,” “relF200,” and “relF250.”
of the trial, we can trim the force-time frame proceeded from the beginning of
the IMTP trial until peak force was The allometrically scaled peak forces
curve to only include the data from the for each epoch were calculated by
start of the trial until peak Fz. Line 143 achieved, we used “iloc[-1]” to find
the last value in the “net_force” column dividing the net force for each epoch
creates another dataframe, called “df2.” by the value labeled “e” and were
This line of code uses the “truncate” of “df2.” Line 151 calculated the peak
net force relative to body mass. This is labeled according to each epoch
method to make a copy of “df1” and (“allF50,” “allF100,” “allF150,”
remove all data before the start of the accomplished by dividing “Peak_-
Force” by “Mass.” This variable was “allF200,” and “allF250”).
trial. Because this method maintains
the original index of df1, we need to labeled “relPeak_Force.” Line 152 cal- Now, we can put these force metrics
reset the index so that the first data culated the allometrically scaled peak into a separate dataframe, which will
point is associated with the index of net force (“allPeak_Force”). This vari- be used later to create a table for our
0. Line 144 uses the “reset_index” able was calculated by dividing the net report. Lines 178–184 created a list of
method to accomplish this task. Now, peak force by the individual’s body information to create the dataframe. This
we have a dataframe that reports the mass raised to the two-thirds power. list is labeled “dict.” The first row in the
first “Fz” value at the start of the trial in Line 150 calculated the body mass list will contain the information for the
the first row of the “Fz” column. How- raised to the two-thirds power and first column, which are “Variable,” “Gross
ever, the “Time” value is still relative to labeled this value as “e.” In Python, Force,” “Net Force,” “Relative Force,”
the start of data collection (i.e., at the using double asterisks (**) denotes and “Allometrically Scaled Force.” The
start of the system weight determina- using an exponent. Therefore, the allo- second row in the list will contain the
tion or earlier). To make the “Time” metrically scaled peak net force in line peak force variables, which will be dis-
values relative to the start of the trial, 152 is calculated by dividing the played in the second column. Each sub-
we need to create a function that will “Peak_Force” by “e.” sequent row in the list will contain the
subtract the time at which the trial Lines 155–175 calculated the gross force data for each epoch (50 ms data in
started from every row in the “Time” peak force, net peak force, relative column 3, 100 ms data in column 4, etc).
column of the “df2” dataframe. Line net force, and allometrically scaled Information contained within the apos-
145 creates a new variable column peak net forces for specific epochs trophes is a string of characters (i.e., text)
called “nTime” in the “df2” dataframe. (50, 100, 150, 200, and 250 ms). Line that will be displayed in the dataframe.
The values in this column were calcu- 155 calculated the gross peak force by Information contained within the brack-
lated by applying a function to each using the “max()” function on the “Fz” ets without apostrophes will be the val-
row in the dataframe. The “apply” column of the “df2” dataframe. The ues previously calculated. Line 185
and “lambda” functions were used to gross peak force for each epoch was converted this list into a dataframe using
create an equation and to apply it to determined by applying the “iloc[]” the method “pd.DataFrame.from_dict.”
each row in the “Time” column of the function. Because the data were This new dataframe was labeled “df3.”
297
Strength and Conditioning Journal | www.nsca-scj.com
Copyright © National Strength and Conditioning Association. Unauthorized reproduction of this article is prohibited.
Python & Isometric Force-Time Curves
dominant limb (“d”) and the left limb as function. The title for this plot was and tables on the computer screen.
the nondominant limb (“n”). Line 237 “IMTP using Weight.” Line 259 cre- Line 273 used PySimpleGUI’s “Can-
calculated the asymmetry index and ated the second graph for the subplot vas” function to create a canvas for
labeled this value as “asymmetry_in- using the “ntime” and “Fz” data from the subplot. The “key” argument was
dex.” If the user has a single force plate, the “df2” dataframe.” Line 260 gener- used as an identifier for the canvas.
they would not be able to calculate ated the title for the second plot. Lines Later in the script, we embedded the
asymmetry index. Therefore, they can 216 and 262 created the final plot by subplot into this canvas. The “size”
skip lines 227–237. plotting the gross force values for each argument provided the dimensions
Lines 238–243 created a list, called limb (“lFz” and “rFz”) from the “df2” for how big the canvas should be.
“dict_RFD” for the RFD data for aver- dataframe along the y-axis and “ntime” The first value indicated the width,
age RFD, RFD at 50 ms, RFD at from the “df2” dataframe along the and the second value indicated the
100 ms, RFD at 150 ms, RFD at x-axis. The “label” arguments for lines height of the canvas in pixels.
200 ms, and RFD at 250 ms. Lines 261 and 262 were used to identify the Lines 274–281 were used to display the
244–248 created a list, called left and right legs on the graph. Line tabular data in 4 different tables on the
“dict_RFDs,” for the RFD for 50– 263 generated the title for this third
computer screen. Lines 274 and 275
100 ms, the RFD for 100–200 ms, the graph, “IMTP for Left and Right Legs.”
were used to display the data from
RFD for 200–250 ms, pRFD, and the Line 264 used the “legend” function to
the “df3” dataframe, which contained
asymmetry index. Again, if the user is display the legend for the third plot. If
our force data. The “values.tolist()”
collecting data from a single force the user collects data from a single
function was used to convert the pan-
plate, they can remove the reference force plate, they would not need lines
das dataframe to a list and used the
to asymmetry index on line 248 of 261–264. In addition, they would re-
values in the table. The “columns.to-
the script. These lists were converted move “ax3” from line 256 and change
list()” function was used to extract
to dataframes, called “df5” and “df6,” the “3” in parentheses on this line to
the column headings from the data-
respectively, on lines 249 and 252. “2,” which changes the number of col-
frame and use them as the first row
Lines 205 and 253 rounded the values umns from 3 to 2.
in the table. The “size” argument was
associated with each dataframe to 1 After creating the subplot, it was saved used to specify the width in characters
decimal place. These dataframes were in the computer’s memory buffer as an and height in rows for the table.
used later in the script to generate ta- image file to be used later in the script Because the text in the first column
bles in our report and display this data to create the report and display the can take up more space than the other
on the GUI. image within the GUI. Line 267 cre- columns, we set the “auto_size_col-
ated a new variable called “subplot_i- umns” argument to “True” to allow
mage_buffer” and assigned it to an Python to adjust the column width
CREATING GRAPHS
instance of the “BytesIO” class, a class based on the text in the column for
To create the 3 graphs that will be dis- within Python’s “io” module. This the first and last table in the layout.
played within the GUI and in the module allowed the user to work with To make the table visually appealing,
report, we used Matplotlib’s pyplot binary data like a file. In this case, we we set the “justification” for each table
library. To arrange the plots side-by- used “BytesIO” to create an in-memory to “center” and the “font” to “Helveti-
side with similar dimensions, we had buffer where the image data were ca” with a font size of “12.” The second
Python create a subplot containing all stored. Line 268 the “plt.savefig” to and third tables had fewer characters in
3 graphs. Line 256 in the script gener- save the subplot into the variable, “sub- the first column, so we did not need to
ated the subplot function to create 1 plot_image_buffer.” The “format” argu- allow Python to autosize the columns.
figure that contained all 3 graphs with ment was used to save the image as In addition, these tables consisted of 2
3 separate axes. Because we wanted the a “PNG” file. When the image is saved
plots to be displayed side-by-side, we rows for each table. So, the “size” argu-
into the buffer, the pointer scrolls ment was set to 40 characters and 2
specified the number of rows to be 1 through the data from the beginning
and the number of columns to be 3. rows. Each “sg.Table” function was
of the file to the end. Line 269 resets contained within its own brackets to
Therefore, Python placed the 3 graphs the position of the pointer to the begin-
within a single row, each taking up 1 have the GUI display the tables below
ning of the file by using the “seek(0)” each other rather than side-by-side.
column across the page. The “figsize” method. This prepared the buffer to be
argument determined the width and read from the start when we called the Line 282 used the “sg.Text” function to
height for the entire subplot. Line image later in the script. display the instructions “Save PDF
257 used the “plot” function to graph Report as:.” Line 283 had 3 elements
the “Time” and “Fz” columns from the CREATING GRAPHICAL DISPLAY displayed on the GUI below these in-
“df1” dataframe for the first plot within OF DATA structions. The first element was an
the subplot. Line 258 created the title Lines 272–285 created a layout that “sg.Input” that displays the file path
for this plot using the “set_title” tells Python how to display the subplot when the user saves the PDF report.
299
Strength and Conditioning Journal | www.nsca-scj.com
Copyright © National Strength and Conditioning Association. Unauthorized reproduction of this article is prohibited.
Python & Isometric Force-Time Curves
sets the column widths for each col- 362. The last line of the script closed
J. Chadwick
umn in inches. The first value in this the GUI window labeled “window2.”
Smith, PhD is
list corresponded to the first column,
a Professor in the
and the last value to the last column. CONCLUSIONS Department of
The “spaceAfter” argument added IMTP and isometric squat testing can Kinesiology at
extra space (10 points) after the table be a useful diagnostic tool for athlete Coastal Carolina
to create some separation between ta- monitoring as peak force, impulse, and University.
bles and improve the visual layout of RFD measures can be obtained from
the PDF document. the ground reaction forces collected
Lines 318–326, 332–340, 346–354, during these tests. In addition, when
and 360–368 configured the styling these tests are performed on 2 force
of each table in the PDF document. plates, limb asymmetries can also be Tsuyoshi
The “setStyle” method was used to evaluated. To ensure the accuracy of Nagatani, MS
instruct Python to use the parameters these tests, a standardized protocol is a PhD candi-
that follow to set the visual style of the that includes a thorough warm-up date in the area
dataframe. The “TableStyle” class in- must be followed to improve test- of Sports Science
structed Python to apply this style to retest reliability. Although these tests and a member of
the table. The first “BACKGROUND” are useful diagnostic tools, the manual the Strength and
line determined the background color calculation of each force-time curve Power Research
for the header of the table. The “(0, 0)” metric or identification of force-onset Group at Edith
refers to the first column and first row. can be time-consuming, especially Cowan
The (21, 0) refers to the last column when analyzing multiple trials for large University.
of the first row. The “(0.8, 0.8, 0.8)” groups of athletes. One strategy for this
specified the RGB color, which is issue is using commercially available
a light gray, to be applied to this first software programs to rapidly analyze Stuart N.
row in the table. Typically, RGB val- isometric trials. However, purchasing Guppy, PhD is
ues range from 0 to 255. In this case, these programs can be cost- a Lecturer of
Python used a floating-point scale, so prohibitive for some users, and often, Exercise and
values ranged between 0 and 1 to how the force-time is filtered and as- Sport Science
determine the RGB values. The sessed is proprietary information. To (Strength &
“TEXTCOLOR” line applied black allow greater control of the analysis Conditioning)
to the text in this first row for each procedures, users can create a template and member of
table. The “ALIGN” line applied cen- in Excel to analyze their isometric data. the Strength and
ter alignment to the entire table. The Analyzing multiple trials using spread- Power Research
“FONTNAME” applied the font type sheet software may be less time- group in the School of Medical and
“Helvetica-Bold” to the first row to efficient than creating a custom script Health Sciences at Edith Cowan
distinguish the column names from to analyze isometric force data. The University.
the rest of the table. The “FONT- focus of this paper was to assist the user
SIZE” line is applied to the table to with creating a custom script using the
make the font size “10.” The “BOT- programming language, Python. The G. Gregory
TOMPADDING” added 8 points of script created by this guide could be Haff, PhD is the
padding below the header column. used to completely automate the anal- Professor of
The last “BACKGROUND” line for ysis of isometric trials or allow for the Strength and
each section specified the background manual selection of the start of each Conditioning,
color, a lighter gray than the back- trial before automating the rest of the and the Director
ground color for the column headings, data analysis. Finally, this paper dis- of the Strength
for the rest of the table, excluding the cussed a method to generate a report and Power
header row. Lines 327, 341, 355, and that can be used to disseminate test Research Group
369 used the “append” method to add results. in the School of
each table to the list labeled “ele- Medical and Health Sciences at Edith
ments.” On line 366, the PDF docu- Cowan University.
ment was generated by calling the
“doc.build (elements).” Finally, the Conflicts of Interest and Source of Funding:
script broke out of the infinite loop The authors report no conflicts of interest REFERENCES
1. Beckham G, Mizuguchi S, Carter C, et al.
with the “break” statement on line and no source of funding. Relationships of isometric mid-thigh pull variables
301
Strength and Conditioning Journal | www.nsca-scj.com
Copyright © National Strength and Conditioning Association. Unauthorized reproduction of this article is prohibited.