Control the behaviour of PyCall

pycall

#1

Hello,

not sure it’s the right place to ask the question, I’ll be happy to ask elsewhere if it’s the case.

The following code is based on this blog post on Medium.

I’m calling basemap through PyCall and when I execute the following code I get the right results, but it triggers a figure. I was wondering how to prevent the figure from appearing. The figure appears when the line poly_paths = m[:drawcoastlines]()[:get_paths]() is executed.

Thanks for any help!

MWE

using PlotlyJS
using PyPlot
using PyCall

const basemap = PyNULL()
copy!(basemap, pyimport_conda("mpl_toolkits.basemap", "basemap"))

m = basemap[:Basemap]()

function polygons_to_traces(poly_paths, N_poly)
    """
    pos arg 1. (poly_paths): paths to polygons
    pos arg 2. (N_poly): number of polygon to convert
    """
    # init. plotting list
    data = Dict(
        "x" => [],
        "y" => [],
        "mode" => "lines",
        "line" => line(color="black"),
        "name" => ""
    )

    for i_poly in 1:N_poly
        poly_path = poly_paths[i_poly]

        # get the Basemap coordinates of each segment
        coords_cc = [vertex for vertex in poly_path[:vertices]]

        # convert coordinates to lon/lat by 'inverting' the Basemap projection
        lon_cc, lat_cc = m(coords_cc[:,1],coords_cc[:,2], inverse=true)

        # add plot.ly plotting options
        append!(data["x"], [lon_cc; NaN])
        # push!(data["x"], NaN)
        append!(data["y"], [lat_cc; NaN])
        # push!(data["y"], NaN)
    end     

    return data
end

function get_coastline_traces()
    poly_paths = m[:drawcoastlines]()[:get_paths](); # coastline polygon paths
    N_poly = 91

    return polygons_to_traces(poly_paths, N_poly)
end

coastlines = get_coastline_traces()

#2

Nevermind! Found a solution. I added the following in the preambule

const plt = PyNULL()
copy!(plt, pyimport_conda("matplotlib.pyplot", "matplotlib"))

add redefined the function as follow

function get_coastline_traces()
    plt[:ioff]()
    poly_paths = m[:drawcoastlines]()[:get_paths](); # coastline polygon paths
    plt[:ion]()
    N_poly = 91

    return polygons_to_traces(poly_paths, N_poly)
end

#3

I might be wrong, but IIRC you should put this line in your __init__ function, otherwise precompilation won’t work. If you don’t care about precompilation, you could just write const basemap = pyimport(...).


#4

Salut,

I should have mentioned that the line is indeed inside the init function of the module file definition (i.e. ClimateTools.jl, not updated yet).

Thanks for the clarification though, the solution is more complete with it. :slight_smile: