I have an array of boolean data like, e.g.,
z = [true true true
true false true
true true true]
I want to make a contour plot of this data, which in this case should just be a 3x3 grid where the central cell is indicated by a line. I tried
using PlotlyJS
z = [true true true
true false true
true true true]
x = range(1,3)
y = range(1,3)
plt = contour(
x = x,
y = y,
z = Int.(.!z),
contours_coloring = "lines",
contours_start = 0,
contours_end = 1,
contours_size = 1,
colorscale = [[0, "black"], [1, "black"]],
line_smoothing = 0,
line_width = 3,
zmin = 0,
zmax = 1,
showscale = false,
)
plot(plt)
But this only produces
Is there some way to create a plot that just marks the central cell?
Without knowing your scenario, it would seem that a heatmap is likely to be a better format than a contour. I say this because your question is implicitly treating data points as data bins. You are asking if there is a way to contour the bins in which points lie. While not composed of contour lines, a heatmap may be clearest way to communicate that you are dealing with bins and not lines. Below is a simple implementation.
using PlotlyJS
z = [true true true
true false true
true true true]
plt = PlotlyJS.heatmap(
x = range(1,size(z)[1]),
y = range(1,size(z)[2]),
z = Int.(.!z),
colorsca
)
PlotlyJS.plot(plt)
But, assuming is not commonly the best approach, so here is a way to create this type of contour plot. To do this, we need to make a mapping of points to bins. For example, anything where 0.5<x<1.5 and 0.5<y<1.5 need to fetch the value of z[1,1]. Then, we can make a contour plot, and (with enough datapoints), the contour will follow around cells.
In the following, I used Plots.jl, but
using PlotlyJS
zRef = [true true true
true false true
true true true]
# creating our mapping function
function fetchReferenceVal(ref::Matrix, xs::Vector{<:Real},ys::Vector{<:Real})
# initializing an empty output
# depending on your scenario, the filling value may need to be changed.
out = fill(1,length(xs),length(ys))
# are x and y going to lie in our matrix?
for (i,x) in enumerate(xs)
!(x >=1 && x <= size(ref)[1]) && continue
for (j,y) in enumerate(ys)
!(y >= 1 && y<= size(ref)[2]) && continue
# ... Fetch associated value
out[i,j] = Int(ref[Int(round(x)),Int(round(y))])
end
end
return out
end
x = [i for i in 0:.01:4]
y = [i for i in 0:.01:4]
z = fetchReferenceVal(zRef, x, y)
plt = PlotlyJS.contour(
x = x,
y = y,
z = z,
contours_coloring = "lines",
contours_start = 0,
contours_end = 1,
contours_size = 1,
colorscale = [[0, "black"], [1, "black"]],
line_smoothing = 0,
line_width = 3,
zmin = 0,
zmax = 1,
showscale = false,
)
PlotlyJS.plot(plt)