Evaluating place kickers means looking far beyond raw conversion percentages. In high-leverage NFL games, field position, game clock, and coaching trust dictate when and where a kicker is deployed. A kicker who converts 95% of their kicks but is only trusted inside 35 yards provides far less tactical value than a kicker who converts 88% while repeatedly being called upon to convert from 50+ yards in hostile environments.
In this project, we analyse the 2022 NFL Big Data Bowl tracking and special teams dataset to determine who truly are the best kickers in the NFL. We evaluate kickers across multiple dimensions:
Distance Reliability: Breaking down conversion rates across specific distance tiers (< 30, 30–39, 40–49, and 50+ yards).
High-Leverage Workload & Leg Strength: Comparing total field goal volume against accuracy on kicks of 45 yards or greater.
We import four files from the NFL Big Data Bowl: games.csv, plays.csv, players.csv, and PFFScoutingData.csv..
library(tidyverse)
library(scales)
# Read datasets
games <- read_csv("games.csv")
plays <- read_csv("plays.csv")
players <- read_csv("players.csv")
pff <- read_csv("PFFScoutingData.csv")
cat("Total Games:", nrow(games), "\n")
## Total Games: 764
cat("Total Plays:", nrow(plays), "\n")
## Total Plays: 19979
table(plays$specialTeamsPlayType)
##
## Extra Point Field Goal Kickoff Punt
## 3488 2657 7843 5991
table(plays$specialTeamsResult)
##
## Blocked Kick Attempt Blocked Punt Downed
## 61 39 834
## Fair Catch Kick Attempt Good Kick Attempt No Good
## 1645 5470 585
## Kickoff Team Recovery Muffed Non-Special Teams Result
## 16 214 101
## Out of Bounds Return Touchback
## 651 5207 5156
We merge the four datasets using left_join(). We join plays with games on gameId, link player biographical details from players by matching kickerId to nflId, and append scouting observations from PFFScoutingData using both gameId and playId.
We also filter for Field Goal attempts with recorded yardage, group by displayName and possessionTeam (to account for players active across multiple rosters), and aggregate career volume, conversion rates, and maximum converted distance.
df <- plays %>%
left_join(games, by = "gameId") %>%
left_join(players, by = c("kickerId" = "nflId")) %>%
left_join(pff, by = c("gameId", "playId"))
# Kicker summary table
kicker_leaderboard <- df %>%
filter(specialTeamsPlayType == "Field Goal", !is.na(kickLength), !is.na(displayName)) %>%
group_by(displayName, possessionTeam) %>%
summarise(
seasons = n_distinct(season),
attempts = n(),
made = sum(specialTeamsResult == "Kick Attempt Good", na.rm = TRUE),
accuracy = made / attempts,
longest_kick = max(kickLength, na.rm = TRUE),
.groups = "drop"
) %>%
filter(seasons > 1, attempts >= 30) %>%
arrange(-accuracy)
# Table of Top 10 Kickers
knitr::kable(
head(kicker_leaderboard %>%
mutate(accuracy = scales::percent(accuracy, accuracy = 0.1)), 10),
caption = "Top 10 NFL Kickers by Overall Field Goal Accuracy (Min. 30 Attempts, >1 Season)"
)
| displayName | possessionTeam | seasons | attempts | made | accuracy | longest_kick |
|---|---|---|---|---|---|---|
| Josh Lambo | JAX | 3 | 57 | 54 | 94.7% | 59 |
| Justin Tucker | BAL | 3 | 92 | 87 | 94.6% | 65 |
| Nick Folk | NE | 2 | 41 | 38 | 92.7% | 51 |
| Harrison Butker | KC | 3 | 84 | 77 | 91.7% | 58 |
| Younghoe Koo | ATL | 2 | 57 | 52 | 91.2% | 54 |
| Jason Myers | SEA | 2 | 44 | 40 | 90.9% | 61 |
| Wil Lutz | NO | 3 | 85 | 77 | 90.6% | 58 |
| Mason Crosby | GB | 3 | 71 | 63 | 88.7% | 56 |
| Chris Boswell | PIT | 3 | 62 | 55 | 88.7% | 59 |
| Aldrick Rosas | NYG | 2 | 44 | 39 | 88.6% | 57 |
To understand where kicker consistency breaks down, we separate every field goal into four distinct distance buckets: < 30 yds, 30-39 yds, 40-49 yds, and 50+ yds. The heatmap below displays the conversion percentage for all qualifying kickers (minimum 35 attempts across multiple seasons), labeled with their exact made/attempted splits.
# Group kicks by distance
tier_data <- df %>%
filter(specialTeamsPlayType == "Field Goal", !is.na(kickLength), !is.na(displayName)) %>%
mutate(
dist_bin = case_when(
kickLength < 30 ~ "< 30 yds",
kickLength >= 30 & kickLength < 40 ~ "30-39 yds",
kickLength >= 40 & kickLength < 50 ~ "40-49 yds",
kickLength >= 50 ~ "50+ yds"
),
dist_bin = factor(dist_bin, levels = c("< 30 yds", "30-39 yds", "40-49 yds", "50+ yds"))
)
# 2. Filter for kickers
qualifying_kickers <- tier_data %>%
group_by(displayName) %>%
summarise(
total_att = n(),
seasons = n_distinct(season),
.groups = "drop"
) %>%
filter(seasons > 1, total_att >= 35)
# 3. Calculate accuracy per distance
heatmap_df <- tier_data %>%
filter(displayName %in% qualifying_kickers$displayName) %>%
group_by(displayName, dist_bin) %>%
summarise(
att = n(),
made = sum(specialTeamsResult == "Kick Attempt Good"),
pct = made / att,
.groups = "drop"
)
# 4. Heatmap plot
ggplot(heatmap_df, aes(x = dist_bin, y = reorder(displayName, pct, FUN = mean), fill = pct)) +
geom_tile(color = "white", linewidth = 0.5) +
geom_text(aes(label = paste0(round(pct * 100), "% (", made, "/", att, ")")),
size = 2.8, fontface = "bold", color = "white") +
scale_fill_gradient(low = "#b2182b", high = "#1b7837", labels = scales::percent_format(accuracy = 1)) +
labs(
title = "Field Goal Accuracy by Distance Bracket",
subtitle = "Evaluating reliability across distances (Min. 35 career attempts)",
x = "Distance Bracket",
y = "Kicker",
fill = "Accuracy"
) +
theme_minimal(base_size = 12) +
theme(
plot.title = element_text(face = "bold", size = 16),
axis.text.y = element_text(size = 9),
axis.text.x = element_text(size = 11, face = "bold"),
panel.grid = element_blank()
)
< 30 yards: Kickers convert at an overall league rate of 98.0%, with elite kickers like Justin Tucker (26/26), Josh Lambo (15/15), and Harrison Butker (27/27) displaying zero room for error.
30–39 yards: Average accuracy holds strong at 93.9%, serving as an expected conversion range across NFL.
40–49 yards: This range reveals the performance difference across the league, with the average dropping to 78.7%. While elite performers like Graham Gano (100%, 13/13) and Justin Tucker (96.6%, 28/29) stay almost perfect, mid-tier kickers slide into the 60%–75% range.
50+ yards: Conversion rates fall to 64.3%, with high variance ranging from 33% (Cairo Santos, 2/6) up to 100% (Younghoe Koo, 7/7).
High-Volume Range Threats: Brandon McManus attempted 21 kicks from 50+ yards (converting 62%), showing immense organizational willingness to attempt long kicks.
Limited Deep Exposure: Kickers like Ryan Succop (3 attempts) and Nick Folk (4 attempts) maintain high deep conversion marks, but on constrained sample sizes that suggest coaches selectively preserve their range.
To isolate true kicking value, we look at the interaction between coaching trust (total attempt volume) and deep accuracy (field goals \(\ge\) 45 yards). Bubble size indicates the kicker’s overall conversion rate across all distances.
# Aggregate long-range kicks (45+ yards) versus total attempts
long_kick_data <- df %>%
filter(specialTeamsPlayType == "Field Goal", !is.na(kickLength), !is.na(displayName)) %>%
group_by(displayName, possessionTeam) %>%
summarise(
seasons = n_distinct(season),
total_fgs = n(),
overall_made = sum(specialTeamsResult == "Kick Attempt Good"),
overall_acc = overall_made / total_fgs,
long_att = sum(kickLength >= 45),
long_made = sum(kickLength >= 45 & specialTeamsResult == "Kick Attempt Good"),
long_acc = ifelse(long_att > 0, long_made / long_att, 0),
.groups = "drop"
) %>%
filter(seasons > 1, total_fgs >= 30, long_att >= 8) %>%
arrange(-long_acc)
# Scatter plot
ggplot(long_kick_data, aes(x = total_fgs, y = long_acc, size = overall_acc, color = long_acc)) +
geom_point(alpha = 0.85) +
geom_text(aes(label = displayName), vjust = -1.2, size = 3.2, check_overlap = TRUE, color = "black") +
scale_color_gradient(low = "#d73027", high = "#313695", labels = scales::percent_format(accuracy = 1)) +
scale_y_continuous(labels = scales::percent_format(accuracy = 1), limits = c(0.45, 1.0)) +
scale_size_continuous(range = c(3, 8), labels = scales::percent_format(accuracy = 1)) +
labs(
title = "Accuracy on 45+ Yard Field Goals vs. Total Workload",
subtitle = "Bubble size represents overall field goal accuracy across all distances",
x = "Total Field Goal Attempts",
y = "Accuracy on 45+ Yard Kicks",
size = "Overall Accuracy",
color = "45+ Yd Accuracy"
) +
theme_minimal(base_size = 12) +
theme(
plot.title = element_text(face = "bold", size = 16),
legend.position = "right"
)
Tucker anchors the upper right quadrant of the scatter plot. He was entrusted with 92 total field goal attempts while maintaining a 90.3% conversion rate (28/31) on kicks of 45+ yards, combined with a 94.6% career baseline.
Younghoe Koo (92.9% on 45+ yard kicks, 13/14) and Josh Lambo (87.5%, 14/16) lead in deep conversion percentage, though across a moderate total volume of 57 attempts.
Kickers such as Ka’imi Fairbairn (96 attempts, 64.3% deep) and Jason Sanders (83 attempts, 68.6% deep) handle heavy league workloads, but encounter clear performance drops beyond 45 yards.
Kickers like Stephen Gostkowski, Jake Elliott, and Dan Bailey convert at roughly 50% to 55% from 45+ yards, representing coin-flip odds from extended range.
By evaluating both distance-bracketed performance and deep-range workload, we reach three core conclusions:
Short-Range Conversion is Table Stakes: All NFL starting kickers convert between 94% and 100% of kicks under 40 yards. Raw accuracy stats are heavily inflated by attempts inside this threshold.
Separation Occurs at 45+ Yards: Elite place-kicking is defined by performance on attempts beyond 40 yards, where league success rates fall from ~94% to ~64%.
The Best Kicker: Justin Tucker represents the gold standard of NFL kicking. He pairs league-leading volume (92 attempts) with elite reliability from different situations (96.6% from 40–49 yards, 90.3% from 45+ yards), eliminating the tradeoff between long-range power and down-to-down accuracy.