0

I'd like to draw a shape similar to the following example (from the Naval Research Laboratory TC page). The shape is defined by 4 radii, one for each quadrant.

sample

I have multiple track centers in latitude and longitude coordinates of which I plot using Basemap:

def m_plot_wind_speeds(x,y, mps):

    # There's a switch-like statement here to determine the color of the
    # line based on wind speed which I ignored. This is passed to the 
    # color kwarg in m.plot as cur_color. 

    m.plot(x,y, '.-', markersize=ms, linewidth=lw, color=cur_color, \
 mew=1.5, markerfacecolor='k')

m = Basemap(projection='cyl',area_thresh=1000, \
    llcrnrlat=southLat,urcrnrlat=northLat,llcrnrlon=westLong,urcrnrlon=eastLong,resolution='h')
parallels = np.arange(southLat,northLat+10,10.) # make latitude lines ever 5 degrees from 30N-50N
meridians = np.arange(westLong,eastLong+30,30.) # make longitude lines every 5 degrees from 95W to 70W

m.drawparallels(parallels,labels=[1,0,0,0],labelstyle="+/-", linewidth=0, fontsize=6)
m.drawmeridians(meridians,labels=[0,0,0,1],labelstyle="+/-", linewidth=0, fontsize=6)
m.drawcountries(linewidth=0.25)

m.bluemarble()

# data is a [10]x[~]x[10] list. There are 10 trajectories, each with
# varying lengths. Each trajectory has 10 attributes.

for traj in data:
    lat = []
    lon = []
    wind_speed=[]

    for i in traj:
        lat.append(float(i[1]))
        lon.append(float(i[0]))
        wind_speed.append(float(i[2]))

   for j,var in enumerate(traj):
        if j > 0:
            x,y = m([lon[j], lon[j-1]], [lat[j], lat[j-1]])
        else:
            x,y = m([lon[j], lon[j]],[lat[j], lat[j]])
        m_plot_wind_speeds(x,y,wind_speed[j])


        # TODO: Insert a function here that takes in a 4 radii and plots them 
        # in each quadrant.
JohanC
  • 71,591
  • 8
  • 33
  • 66
Johndo
  • 1
  • 1

1 Answers1

1

If you don't mind having lines towards the center, wedges can be used.

Alternatively, using arcs, hlines and vlines, the outline can be drawn. You'd still need either wedges or a specially crafted polygon to fill.

import numpy as np
from matplotlib import patches
import matplotlib.pyplot as plt

def draw_quadrants_arcs(xcenter, ycenter, radii, lw=2, ec='crimson', ax=None):
    ax = ax or plt.gca()
    for rad, theta in zip(radii, [0, 90, 180, 270]):
        arc = patches.Arc((xcenter, ycenter), 2*rad, 2*rad, theta1=theta, theta2=theta+90,
                              lw=lw, ec=ec, fc='none')
        ax.add_patch(arc)
    ax.hlines([ycenter, ycenter], [xcenter + radii[0], xcenter - radii[1]], [xcenter + radii[3], xcenter - radii[2]],
              lw=lw, colors=ec)
    ax.vlines([xcenter, xcenter], [ycenter + radii[0], ycenter - radii[2]], [ycenter + radii[1], ycenter - radii[3]],
              lw=lw, colors=ec)

def draw_quadrants_wedges(xcenter, ycenter, radii, lw=2, ec='crimson', fc='lime', alpha=1, ax=None):
    ax = ax or plt.gca()
    for rad, theta in zip(radii, [0, 90, 180, 270]):
        wedge = patches.Wedge((xcenter, ycenter), rad, theta, theta + 90,
                              lw=lw, ec=ec, fc=fc, alpha=alpha)
        ax.add_patch(wedge)

xcenter, ycenter = 6, 10
radii = [6, 2, 4, 7]
# only wedges
draw_quadrants_wedges(xcenter, ycenter, radii)
# only arcs
draw_quadrants_arcs(xcenter+12, ycenter, radii)
# wedges and arcs together
draw_quadrants_wedges(xcenter+24, ycenter, radii, ec='none', lw=0, fc='limegreen', alpha=0.3)
draw_quadrants_arcs(xcenter+24, ycenter, radii)

plt.xlim(0, 40)
plt.ylim(0, 20)
plt.gca().set_aspect('equal', 'box')
plt.show()

example plot

JohanC
  • 71,591
  • 8
  • 33
  • 66
  • If this answers your question, you might consider clicking the check mark to mark the answer as accepted. – JohanC Mar 17 '20 at 16:23