Python 3.x 如何在cartopy';使用python创建geoaxes?
我正在尝试为cartopy matplotlib绘图实现斑马样式 这是用于生成地理地图的常用打印样式。一些地理信息系统已经实现了这种方式。然而,Python并不拥有它 我已经成功地生成了一个函数,可以在给定的cartopy的GeoAxis中添加斑马状的蜱虫 尽管如此,尽管我努力更新算法,但我无法允许自动更新斑马蜱的坐标。此更新将允许解决诸如event.callbacks.connect操作(即:放大、缩小或打印拖动)之类的问题,在这些操作中,斑马形记号会丢失其在轴中的位置 如果可能,我希望确保每次用户应用某种缩放或拖动操作时,相应的斑马状刻度也会自动更新 我已经尝试为matplotlib的callbacks.connect方法实现类的概念,如和所述 以下是迄今为止的脚本:Python 3.x 如何在cartopy';使用python创建geoaxes?,python-3.x,matplotlib,cartopy,Python 3.x,Matplotlib,Cartopy,我正在尝试为cartopy matplotlib绘图实现斑马样式 这是用于生成地理地图的常用打印样式。一些地理信息系统已经实现了这种方式。然而,Python并不拥有它 我已经成功地生成了一个函数,可以在给定的cartopy的GeoAxis中添加斑马状的蜱虫 尽管如此,尽管我努力更新算法,但我无法允许自动更新斑马蜱的坐标。此更新将允许解决诸如event.callbacks.connect操作(即:放大、缩小或打印拖动)之类的问题,在这些操作中,斑马形记号会丢失其在轴中的位置 如果可能,我希望确保每
import matplotlib.pyplot as plt
import cartopy.crs as ccrs
import cartopy.feature as cfeature
import matplotlib.patches as mpatches
from matplotlib.offsetbox import AnchoredText
from cartopy.mpl.geoaxes import GeoAxesSubplot
class zebra_ticks():
def __init__(self, ax=None,
projection = ccrs.PlateCarree(),
drawlicense=True,
pad=2):
if not isinstance(ax, GeoAxesSubplot):
self.fig = plt.figure(figsize=(9,7))
self.ax = plt.axes(projection=projection)
# Put a background image on for nice sea rendering.
self.ax.stock_img()
# Create a feature for States/Admin 1 regions at 1:50m from Natural Earth
states_provinces = cfeature.NaturalEarthFeature(
category='cultural',
name='admin_1_states_provinces_lines',
scale='50m',
facecolor='none')
SOURCE = 'Natural Earth'
LICENSE = 'public domain'
self.ax.add_feature(cfeature.LAND)
self.ax.add_feature(cfeature.COASTLINE)
self.ax.add_feature(states_provinces, edgecolor='gray')
# Add a text annotation for the license information to the
# the bottom right corner.
if drawlicense:
text = AnchoredText(r'$\mathcircled{{c}}$ {}; license: {}'
''.format(SOURCE, LICENSE),
loc='right',
bbox_transform=self.ax.transAxes,
bbox_to_anchor=(1.01, -0.11),
prop={'size': 8},
frameon=False)
self.ax.add_artist(text)
self.gridliner = self.ax.gridlines(draw_labels=True)
self.pad = pad
self.zebras = self.add_zebra()
plt.show()
self.ax.callbacks.connect('xlim_changed', lambda x: self.update_zebra)
self.ax.callbacks.connect('ylim_changed', lambda x: self.update_zebra)
def add_zebra(self):
'''
Description:
This function add a zebra line border around a cartopy's geoaxes.
It uses the coordinates tick position to evaluate the zebra blocks.
returns (dict): {'horizontal:'horizontal_zebras, 'vertical':vertical_zebras}
'''
self.fig.canvas.draw()
lon0, lon1, lat0, lat1 = self.ax.get_extent(crs=self.ax.projection)
ysegs = self.gridliner.yline_artists[0].get_segments()
yticks = [yseg[0,1] for yseg in ysegs]
xsegs = self.gridliner.xline_artists[0].get_segments()
xticks = [xseg[0,0] for xseg in xsegs]
xticks.append(lon1)
i = 0
colors_wk = ['white', 'black']
horizontal_zebras={'north':[],
'south':[]}
vertical_zebras={'east':[],
'west':[]}
for lon, position in zip([lon0, lon1 - self.pad], ['east', 'west']):
y0 = xticks[0]
for enum, y in enumerate(yticks[1:]):
color = colors_wk[i]
delta_coor = (y - y0)
vertical_rect = mpatches.Rectangle( (lon, y0), self.pad , delta_coor,
transform=self.ax.transData,
facecolor=color, zorder=1000)
vertical_zebras[position].append(vertical_rect)
i = 1 - i
y0 = y
self.ax.add_patch(vertical_rect)
for lat, position in zip([lat0, lat1 - self.pad], ['south', 'north']):
x0 = xticks[0]
for x in xticks[1:]:
color = colors_wk[i]
delta_coor = (x - x0)
horizontal_rect = mpatches.Rectangle( (x0, lat), delta_coor, self.pad ,
transform=self.ax.transData,
facecolor=color, zorder=1000)
horizontal_zebras[position].append(horizontal_rect)
x0 = x
i = 1 - i
self.ax.add_patch(horizontal_rect)
if self.ax.projection.proj4_params.get('units', 'None') == 'None':
if not (lon0 <=-180 or lon1 >= 180 or lat0>=90 or lat0<=-90):
self.ax.set_extent((lon0-self.pad,
lon1+self.pad,
lat0-self.pad,
lat1+self.pad))
return {'horizontal':horizontal_zebras,
'vertical':vertical_zebras}
def update_zebra(self, event):
axes = event.axes
# trigger the outline and background patches to be re-clipped
axes.outline_patch.reclip = True
axes.background_patch.reclip = True
lon0, lon1, lat0, lat1 = self.ax.get_extent(crs=self.ax.projection)
ysegs = self.gridliner.yline_artists[0].get_segments()
yticks = [yseg[0,1] for yseg in ysegs]
xsegs = self.gridliner.xline_artists[0].get_segments()
xticks = [xseg[0,0] for xseg in xsegs]
xticks.append(lon1)
for Vzebras in self.zebras['vertical']:
for zebra in Vzebras:
for lon, position in zip([lon0, lon1 - self.pad], ['east', 'west']):
y0 = xticks[0]
for enum, y in enumerate(yticks[1:]):
delta_coor = (y - y0)
zebra.set_bounds( lon, y0, self.pad , delta_coor)
y0 = y
for Hzebras in self.zebras['vertical']:
for zebra in Hzebras:
for lat, position in zip([lat0, lat1 - self.pad], ['south', 'north']):
x0 = xticks[0]
for x in xticks[1:]:
delta_coor = (x - x0)
zebra.set_bounds( x0, lat,
delta_coor,
self.pad )
x0 = y
if '__main__' == __name__:
Z = zebra_ticks()
导入matplotlib.pyplot作为plt
将cartopy.crs作为CCR导入
将cartopy.feature导入为cfeature
将matplotlib.patches作为MPatch导入
从matplotlib.offsetbox导入锚定文本
从cartopy.mpl.geoaxes导入GeoAxesSubplot
类斑马蜱():
def uuu init uuu(self,ax=None,
投影=ccrs.PlateCarree(),
drawlicense=True,
pad=2):
如果不存在(ax、GeoAxesSubplot):
self.fig=plt.figure(图大小=(9,7))
self.ax=plt.轴(投影=投影)
#将背景图像放在屏幕上,以进行漂亮的海洋渲染。
self.ax.stock_img()
#为距离自然地球1:50米的州/行政区创建要素
州/省=cfeature.NaturalEarthFeature(
“文化”类,
name='admin'u 1'州\省\线',
比例尺='50m',
facecolor='none')
来源=‘自然地球’
许可证='公共域'
self.ax.add_特征(cfeature.LAND)
self.ax.add_特征(C特征.海岸线)
self.ax.add\u功能(州/省,edgecolor='gray')
#将许可证信息的文本批注添加到
#右下角。
如果获得许可证:
text=AnchoredText(r'$\mathcircled{{{c}}}${};许可证:{}'
''格式(来源、许可证),
loc='right',
bbox_transform=self.ax.transAxes,
bbox_至_锚=(1.01,-0.11),
prop={'size':8},
frameon=False)
self.ax.add_艺术家(文本)
self.gridliner=self.ax.gridlines(draw\u labels=True)
self.pad=pad
self.zebras=self.add_zebra()
plt.show()
self.ax.callbacks.connect('xlim\u changed',lambda x:self.update\u zebra)
self.ax.callbacks.connect('ylim\u changed',lambda x:self.update\u zebra)
def添加斑马(自身):
'''
说明:
此函数用于在cartopy的地理轴周围添加斑马线边框。
它使用坐标记号位置来计算斑马块。
返回(dict):{'horizontal:'horizontal_斑马,'vertical':vertical_斑马}
'''
self.fig.canvas.draw()
lon0,lon1,lat0,lat1=self.ax.get_区段(crs=self.ax.projection)
ysegs=self.gridliner.yline\u艺术家[0]。获取分段()
yticks=[yseg[0,1]表示yseg中的yseg]
xsegs=self.gridliner.xline_艺术家[0]。获取_段()
xticks=[xseg[0,0]表示xsegs中的xseg]
xticks.append(lon1)
i=0
颜色_wk=[“白色”、“黑色”]
水平斑马={'north':[],
“南部”:[]}
垂直斑马={'east':[],
“西部”:[]}
对于lon,在拉链中定位([lon0,lon1-self.pad],“东”,“西]):
y0=xticks[0]
对于枚举,枚举中的y(yticks[1:]):
颜色=颜色\u wk[i]
delta_coor=(y-y0)
垂直矩形=匹配矩形((lon,y0),自焊盘,三角形,
转换=self.ax.transData,
facecolor=color,zorder=1000)
垂直斑马[position]。追加(垂直方向)
i=1-i
y0=y
self.ax.add_patch(垂直方向)
对于lat,在zip中定位([lat0,lat1-self.pad],“南”,“北]):
x0=xticks[0]
对于xticks[1:]中的x:
颜色=颜色\u wk[i]
delta_coor=(x-x0)
水平矩形=mpatches.矩形((x0,横向),三角形,自焊盘,
转换=self.ax.transData,
facecolor=color,zorder=1000)
水平斑马[position]。追加(水平方向)
x0=x
i=1-i
self.ax.add_补丁(水平方向)
如果self.ax.projection.proj4_params.get('units','None')=='None':
如果不是(Lo0=180或LAT0>=90或LAT0),你就永远不能调用<代码>自己。UpDeTeY.ZEBRA < /Case>方法。考虑<代码> lambda x:NoPy.Sin < /C> >,它不计算任何东西的正弦。亲爱的ImportanceOfBeingErnest,我应该怎样在哪里做?你能发布更详细的答案吗?