def plot_annloss_deagg_distmag(data, momag_labels, range_bins, pct_limits=None,
                               output_file=None, title=None,
                               show_graph=False, grid=False, colormap=None,
                               annotate=[]):
    """Plot annualised loss deaggregated distance/magnitude data.

    Inputs:
    data         an MxN array containing % annualised loss values with axes
                 of moment/magnitude data (M) versus distance (N)
    momag_labels an iterable containing the y-axis labels for each row of 'data'
    range_bins   an iterable of range values for each column of 'data'
    pct_limits   a tuple (min_pct, max_pct) for % range to plot
    output_file  path to required output plot file
    title        string used to title graph
    show_graph   if True shows graph in window on screen
    grid         if True puts a grid in the graph
    colormap     name of the colormap to use
    annotate     an iterable like [(x, y, str, dict), ...] where
                     x    is X screen coordinate
                     y    is Y screen coordinate
                     str  is the annotation string to display at (x, y)
                     dict is a dictionary of key/value pairs as documented at
                          http://matplotlib.sourceforge.net/api/pyplot_api.html
                          (this is optional)
                 NOTE: if annotate=None is used, no automatic annotation occurs.
                       if annotate=[] is used, auto annotation is generated:
                           timestamp
                           clipping
                           max input data value

    """

    # decide if we have a 'gui-less' plot or not.
    import matplotlib
    if output_file and not show_graph:
        # no plot to be shown - no gui
        matplotlib.use('Agg', warn=False)
    elif show_graph:
        # decide if we *can* show the plot - error if not
        if sys.platform != 'win32':
            try:
                display = os.environ['DISPLAY']
            except KeyError:
                msg = ("No DISPLAY variable set.  "
                       "Did you do 'ssh -X <machine>'?")
                raise RuntimeError(msg)

    # go ahead with the plot
    import matplotlib.pyplot as plt
    import matplotlib.colors as mcolors

    # decide if we are going to plot
    if output_file or show_graph:
        # get colormap to use
        (cmap_name, my_cmap) = uc.get_colormap(colormap)

        # get maximum data value
        #max_pct = scipy.max(data)
        max_pct = num.max(data)
        
        # limit values to within pct_limits here
        if pct_limits:
            (floor, ceil) = pct_limits
            plot_data = scipy.clip(data, floor, ceil)
        else:
            plot_data = data

        # drop last range bin row from data
        plot_data = plot_data[:,:-1]
        
        # Get data X and Y limits
        max_x = range_bins[-1]
        min_x = range_bins[0]
        max_y = momag_labels[-1]
        min_y = momag_labels[0]
        max_z = num.max(plot_data)
        min_z = num.min(plot_data)

        # calculate required aspect ration (the *2 is a fudge)
        (y_size, x_size) = scipy.shape(plot_data)
        ratio = float(x_size/y_size) * 2

        # start plot
        fig = plt.figure()
        ax = fig.add_subplot(111)

        im = plt.imshow(plot_data, interpolation='nearest', cmap=my_cmap,
                        origin='lower', extent=[min_x,max_x,min_y,max_y])

        # add color bar
        for step in (1, 2, 5, 10, 20, 50, 100):
            cb_ticks = [x for x in range(int(min_z), int(max_z+1), step)]
            if len(cb_ticks) <= 12:
                break
        cb = plt.colorbar(orientation='horizontal', ticks=cb_ticks)
        cb.set_label('% of annual loss')
        
        # label axes
        plt.xlabel('Distance (km)')
        plt.ylabel('Moment Magnitude')

        # set main plot aspect ratio
        plt.axes().set_aspect(ratio)

        # add graph 'furniture'
        if title:
            plt.title(title)
        plt.grid(grid) 
                
        # add system annotations: the clipping in effect, time generated, etc
        if isinstance(annotate, list):
            pts.plot_timestamp(fig)

            if pct_limits:
                clip_str = 'Data values clipped to [%.1f,%.1f]' % (floor, ceil)
                plt.text(0.98, 0.02, clip_str, fontsize=6,
                         transform=fig.transFigure, horizontalalignment='right')
            pct_str = '%.2f%%' % max_pct
            plt.text(0.91, 0.185, pct_str, horizontalalignment='left',
                     fontsize=8, transform=fig.transFigure, )

        # add user annotations, if any
        pua.plot_user_annotation(fig, annotate)

        # show or save graph (or both?)
        if output_file:
            plt.savefig(output_file)
        if show_graph:
            plt.show()

        plt.close()
Exemple #2
0
def plot_hexbin_map(map_data, bins=100, title='', output_file=None, cblabel='',
                    cbformat='%.1f', show_graph=False, grid=True, colormap=None,
                    annotate=[], scale=None, np_posn=None,
                    hexbin_args=None, map_extent=None):
    """Plot data into a hexgrid  with an underlay map.

    Inputs:
    map_data       (nx3) array containing the data to plot. The first column
                   contains the latitude of a point, the second column contains
                   the longitude and the third column is the value to bin&plot.
    bins           Either a scalar (# bins in X and Y directions) or (nx, ny).
    title          the graph title string
    output_file    path of file to save plot picture in
    cblabel        label to display on the colorbar
    cbformat       format string used to show colormap values
    show_graph     show graph on screen if True
    grid           draw a grid on graph if True
    colormap       if supplied, the colormap name to use (string)
    annotate       an iterable like [(x, y, ann, dict), ...] where
                       x    is X screen coordinate
                       y    is Y screen coordinate
                       ann  is the annotation string to display at (x, y)
                       dict is a dictionary of key/value pairs as documented at
                            http://matplotlib.sourceforge.net/api/pyplot_api.html
                            (this is optional)
                   NOTE: if annotate=None is used, no automatic annotation occurs.
                         if annotate=[] is used, auto annotation is generated:
                             timestamp
    scale          a tuple containing data used to draw a scale:
                   (posn, length, scale_args)
                   where 'posn'       is where to place scale, one of:
                                          'NW', 'NE', 'SW', 'SE'
                                          (case-insensitive)
                     and 'scale_args' is an optional kwargs dictionary
                   see drawmapscale() function at 
                   http://matplotlib.sourceforge.net/basemap/doc/html/api/basemap_api.html#mpl_toolkits.basemap.Basemap.drawmapscale
                   to see values in scale_args
    np_posn        position tuple or a string describing pointer position:
                       'NW', 'NE', 'SW' or 'SE'
                       (case-insensitive)
    hexbin_args    is a dictionary of hexbin() parameters
                   if not supplied, assume {'gridsize': 100,
                                            'reduce_C_function': scipy.sum
                                           }
                   Note: if hexbin_args is supplied but key 'reduce_C_function'
                   isn't supplied in dictionary, insert 'scipy.sum' function
                   Note: allowed values are documented at:
                         http://matplotlib.sourceforge.net/api/pyplot_api.html
    map_extent     sets the extent of the displayed map if supplied
                   (get extent from the data if not supplied)

    """

    # decide if we have a 'gui-less' plot or not.
    import matplotlib
    if output_file and not show_graph:
        # no plot to be shown - no gui
        matplotlib.use('Agg', warn=False)
    elif show_graph:
        # decide if we *can* show the plot - error if not
        if sys.platform != 'win32':
            try:
                display = os.environ['DISPLAY']
            except KeyError:
                msg = ("No DISPLAY variable set.  "
                       "Did you do 'ssh -X <machine>'?")
                raise RuntimeError(msg)

    # go ahead with the plot
    import matplotlib.pyplot as plt
    import matplotlib.colors as mcolors
    from mpl_toolkits.basemap import Basemap
    from matplotlib.mlab import griddata

    # create a 'binned' plot on a map
    if output_file or show_graph:
        # decide on the colormap to use
        (cmap_name, my_cmap) = uc.get_colormap(colormap)

        # set the hexbin params
        if hexbin_args is None:
            hexbin_args = {'gridsize': 100,
                           'reduce_C_function': scipy.sum,
                           'linewidth': DEFAULT_LINEWIDTH}

        try:
            _ = hexbin_args['reduce_C_function']
        except KeyError:
            hexbin_args['reduce_C_function'] = scipy.sum

        # here we fiddle with 'linewidth' to get around a bug in plotting
        # if linewidth not set, hex bins overlap each other
        # force linewidth to a small value if not specified
        try:
            _ = hexbin_args['linewidth']
        except KeyError:
            hexbin_args['linewidth'] = DEFAULT_LINEWIDTH


        # if user doesn't define 'edgecolors' at all, use default
        hexbin_args['edgecolors'] = hexbin_args.get('edgecolors', FILL_COLOUR)

        # get extent of point data
        if map_extent:
            extent = map_extent
        else:
            extent = gxe.get_extent(map_data, margin=5)
        (ll_lat, ll_lon, ur_lat, ur_lon) = extent

        # start the plot
        fig = plt.figure()
        ax = fig.add_subplot(111)
            
        # draw the map
        m = Basemap(projection='cyl', llcrnrlat=ll_lat, urcrnrlat=ur_lat,
                    llcrnrlon=ll_lon, urcrnrlon=ur_lon, resolution='h',
                    suppress_ticks=False, area_thresh=0.5)

#        m = Basemap(projection='cass', llcrnrlat=ll_lat, urcrnrlat=ur_lat,
#                    llcrnrlon=ll_lon, urcrnrlon=ur_lon, resolution='h',
#                    lat_0=(ll_lat+ur_lat)/2.0, lon_0=(ll_lon+ur_lon)/2.0,
#                    suppress_ticks=False) #, area_thresh=0.5)

        # draw hexbin data on map
        plt.hexbin(map_data[:,0], map_data[:,1], map_data[:,2],
                   cmap=my_cmap, zorder=4, **hexbin_args)

        # draw the other minor stuff
        m.fillcontinents(color=FILL_COLOUR, zorder=2)
        m.drawcoastlines(linewidth=0.25, color='k', zorder=5)
        m.drawmapboundary()

        cb = plt.colorbar(cmap=my_cmap, format=cbformat)
        cb.set_label(cblabel)
        
        plt.xlabel('longitude', fontsize=8)
        plt.ylabel('latitude', fontsize=8)

        # if user asked for a NORTH pointer
        if np_posn:
            unp.plot_northpointer(m, (ll_lat, ll_lon, ur_lat, ur_lon),
                                  np_posn)

        # add graph 'furniture'
        plt.title(title)
        plt.grid(grid, color='#C0C0C0', linestyle='-', linewidth=0.25)

        # add system annotations: time generated, etc
        if isinstance(annotate, list):
            pts.plot_timestamp(fig)

        # add user annotations, if any
        pua.plot_user_annotation(fig, annotate)

        # show or save graph (or both?)
        if output_file:
            plt.savefig(output_file, dpi=300)
        if show_graph:
            plt.show()

        plt.close()
Exemple #3
0
def plot_hexbin_map(map_data,
                    bins=100,
                    title='',
                    output_file=None,
                    cblabel='',
                    cbformat='%.1f',
                    show_graph=False,
                    grid=True,
                    colormap=None,
                    annotate=[],
                    scale=None,
                    np_posn=None,
                    hexbin_args=None,
                    map_extent=None):
    """Plot data into a hexgrid  with an underlay map.

    Inputs:
    map_data       (nx3) array containing the data to plot. The first column
                   contains the latitude of a point, the second column contains
                   the longitude and the third column is the value to bin&plot.
    bins           Either a scalar (# bins in X and Y directions) or (nx, ny).
    title          the graph title string
    output_file    path of file to save plot picture in
    cblabel        label to display on the colorbar
    cbformat       format string used to show colormap values
    show_graph     show graph on screen if True
    grid           draw a grid on graph if True
    colormap       if supplied, the colormap name to use (string)
    annotate       an iterable like [(x, y, ann, dict), ...] where
                       x    is X screen coordinate
                       y    is Y screen coordinate
                       ann  is the annotation string to display at (x, y)
                       dict is a dictionary of key/value pairs as documented at
                            http://matplotlib.sourceforge.net/api/pyplot_api.html
                            (this is optional)
                   NOTE: if annotate=None is used, no automatic annotation occurs.
                         if annotate=[] is used, auto annotation is generated:
                             timestamp
    scale          a tuple containing data used to draw a scale:
                   (posn, length, scale_args)
                   where 'posn'       is where to place scale, one of:
                                          'NW', 'NE', 'SW', 'SE'
                                          (case-insensitive)
                     and 'scale_args' is an optional kwargs dictionary
                   see drawmapscale() function at 
                   http://matplotlib.sourceforge.net/basemap/doc/html/api/basemap_api.html#mpl_toolkits.basemap.Basemap.drawmapscale
                   to see values in scale_args
    np_posn        position tuple or a string describing pointer position:
                       'NW', 'NE', 'SW' or 'SE'
                       (case-insensitive)
    hexbin_args    is a dictionary of hexbin() parameters
                   if not supplied, assume {'gridsize': 100,
                                            'reduce_C_function': scipy.sum
                                           }
                   Note: if hexbin_args is supplied but key 'reduce_C_function'
                   isn't supplied in dictionary, insert 'scipy.sum' function
                   Note: allowed values are documented at:
                         http://matplotlib.sourceforge.net/api/pyplot_api.html
    map_extent     sets the extent of the displayed map if supplied
                   (get extent from the data if not supplied)

    """

    # decide if we have a 'gui-less' plot or not.
    import matplotlib
    if output_file and not show_graph:
        # no plot to be shown - no gui
        matplotlib.use('Agg', warn=False)
    elif show_graph:
        # decide if we *can* show the plot - error if not
        if sys.platform != 'win32':
            try:
                display = os.environ['DISPLAY']
            except KeyError:
                msg = ("No DISPLAY variable set.  "
                       "Did you do 'ssh -X <machine>'?")
                raise RuntimeError(msg)

    # go ahead with the plot
    import matplotlib.pyplot as plt
    import matplotlib.colors as mcolors
    from mpl_toolkits.basemap import Basemap
    from matplotlib.mlab import griddata

    # create a 'binned' plot on a map
    if output_file or show_graph:
        # decide on the colormap to use
        (cmap_name, my_cmap) = uc.get_colormap(colormap)

        # set the hexbin params
        if hexbin_args is None:
            hexbin_args = {
                'gridsize': 100,
                'reduce_C_function': scipy.sum,
                'linewidth': DEFAULT_LINEWIDTH
            }

        try:
            _ = hexbin_args['reduce_C_function']
        except KeyError:
            hexbin_args['reduce_C_function'] = scipy.sum

        # here we fiddle with 'linewidth' to get around a bug in plotting
        # if linewidth not set, hex bins overlap each other
        # force linewidth to a small value if not specified
        try:
            _ = hexbin_args['linewidth']
        except KeyError:
            hexbin_args['linewidth'] = DEFAULT_LINEWIDTH

        # if user doesn't define 'edgecolors' at all, use default
        hexbin_args['edgecolors'] = hexbin_args.get('edgecolors', FILL_COLOUR)

        # get extent of point data
        if map_extent:
            extent = map_extent
        else:
            extent = gxe.get_extent(map_data, margin=5)
        (ll_lat, ll_lon, ur_lat, ur_lon) = extent

        # start the plot
        fig = plt.figure()
        ax = fig.add_subplot(111)

        # draw the map
        m = Basemap(projection='cyl',
                    llcrnrlat=ll_lat,
                    urcrnrlat=ur_lat,
                    llcrnrlon=ll_lon,
                    urcrnrlon=ur_lon,
                    resolution='h',
                    suppress_ticks=False,
                    area_thresh=0.5)

        #        m = Basemap(projection='cass', llcrnrlat=ll_lat, urcrnrlat=ur_lat,
        #                    llcrnrlon=ll_lon, urcrnrlon=ur_lon, resolution='h',
        #                    lat_0=(ll_lat+ur_lat)/2.0, lon_0=(ll_lon+ur_lon)/2.0,
        #                    suppress_ticks=False) #, area_thresh=0.5)

        # draw hexbin data on map
        plt.hexbin(map_data[:, 0],
                   map_data[:, 1],
                   map_data[:, 2],
                   cmap=my_cmap,
                   zorder=4,
                   **hexbin_args)

        # draw the other minor stuff
        m.fillcontinents(color=FILL_COLOUR, zorder=2)
        m.drawcoastlines(linewidth=0.25, color='k', zorder=5)
        m.drawmapboundary()

        cb = plt.colorbar(cmap=my_cmap, format=cbformat)
        cb.set_label(cblabel)

        plt.xlabel('longitude', fontsize=8)
        plt.ylabel('latitude', fontsize=8)

        # if user asked for a NORTH pointer
        if np_posn:
            unp.plot_northpointer(m, (ll_lat, ll_lon, ur_lat, ur_lon), np_posn)

        # add graph 'furniture'
        plt.title(title)
        plt.grid(grid, color='#C0C0C0', linestyle='-', linewidth=0.25)

        # add system annotations: time generated, etc
        if isinstance(annotate, list):
            pts.plot_timestamp(fig)

        # add user annotations, if any
        pua.plot_user_annotation(fig, annotate)

        # show or save graph (or both?)
        if output_file:
            plt.savefig(output_file, dpi=300)
        if show_graph:
            plt.show()

        plt.close()