NOAA GOES 19 Global Lightning Mapper case viewer
This notebook produces an interactive visualization of archived lightning strokes for a user-specified time range
import pandas as pd
import warnings
from datetime import datetime as dt, timezone, timedelta
import geopandas as gpd
import geoviews as gv
from geoviews import opts
from holoviews.element.tiles import OSM, EsriImagery
from lonboard import viz, Map, ScatterplotLayerSpecify the start date and time of the analysis window.
sd = dt(2025, 10, 29, 0)ed = sd + timedelta(hours=6)sddatetime.datetime(2025, 10, 29, 0, 0)eddatetime.datetime(2025, 10, 29, 6, 0)timeString = sd.strftime("%Y%m%d")
timeString'20251029'warnings.simplefilter("ignore")gv.extension('bokeh', 'matplotlib')Open the desired lightning dataset¶
file = f'/spare11/atm533/data/{timeString}_goes19_glm.parquet'
%time df = pd.read_parquet(file)CPU times: user 51.1 ms, sys: 35.8 ms, total: 86.9 ms
Wall time: 43.4 ms
Apply a mask so that only those events in the requested time range are kept
mask = (df['time_start'] > sd) & (df['time_start'] <= ed) df = df.loc[mask]dfAssign the individual time of strokes to a time bin.¶
binInterval = '5min'time_bins= pd.date_range(sd, ed, freq=binInterval)
df['TimeBin'] = df['time_start'].dt.round(binInterval)dfCreate a GeoViews Dataset instance. We pass up to three arguments:¶
The Pandas dataframe
A list containing the
kdims, aka key dimensions, the independent variables: time, lon and latA list containing the
vdims, aka variable dimensions, the dependent variables that vary according to thekdims. Choose the columns we are interested in plotting.
kdims = ['TimeBin','lon','lat']
vdims = ['flash_energy']
gv_ds = gv.Dataset(df,kdims) # no dependent variables, so no vdimsNow create GeoViews Points instances for the desired classes of lightning strokes.¶
Pass only the lon and lat dimensions as the first argument; the time dimension should become interactive.
Specify the width and height of the interactive plot. Adjust as necessary depending on what size display you are using.
plotWidth, plotHeight = 1200, 900points = gv_ds.to(gv.Points, ['lon','lat'])
points.opts(color='red',size=8,marker='x',width=plotWidth, height=plotHeight, framewise=False);Create and render the interactive plot.¶
Layer the desired classes of strokes over a background map.
layout = ( gv.tile_sources.OSM * points)
layout.opts(opts.Points(framewise=False,tools=['hover']))
layoutLonboard can very quickly read and render data from Geopandas dataframes (i.e., those that have a geo-relevant column, e.g. Points, Polygons, and/or MultiPolygons. Let’s read in and visualize the daily GLM file, which was already converted into Geopandas format.
glm_gdf = gpd.read_parquet(f'/spare11/atm533/data/{timeString}_goes19_glm_geo.parquet')viz(glm_gdf)