Skip to content

Commit

Permalink
merge master
Browse files Browse the repository at this point in the history
  • Loading branch information
SimonDanisch committed Sep 18, 2023
2 parents 6471996 + fdc84b8 commit d4f6ce8
Show file tree
Hide file tree
Showing 15 changed files with 373 additions and 269 deletions.
6 changes: 3 additions & 3 deletions GLMakie/src/drawing_primitives.jl
Original file line number Diff line number Diff line change
Expand Up @@ -74,9 +74,9 @@ end

function handle_intensities!(attributes, plot)
color = plot.calculated_colors
if color[] isa Makie.ColorMap
if color[] isa Makie.ColorMapping
attributes[:intensity] = color[].color_scaled
interp = color[].categorical[] ? :nearest : :linear
interp = color[].color_mapping_type[] === Makie.continuous ? :linear : :nearest
attributes[:color_map] = Texture(color[].colormap; minfilter=interp)
attributes[:color_norm] = color[].colorrange_scaled
attributes[:nan_color] = color[].nan_color
Expand Down Expand Up @@ -427,7 +427,7 @@ function draw_atomic(screen::Screen, scene::Scene, heatmap::Heatmap)
t = Makie.transform_func_obs(heatmap)
mat = heatmap[3]
space = heatmap.space # needs to happen before connect_camera! call
xypos = map(t, heatmap[1], heatmap[2], space) do t, x, y, space
xypos = lift(t, heatmap[1], heatmap[2], space) do t, x, y, space
x1d = xy_convert(x, size(mat[], 1))
y1d = xy_convert(y, size(mat[], 2))
# Only if transform doesn't do anything, we can stay linear in 1/2D
Expand Down
34 changes: 33 additions & 1 deletion ReferenceTests/src/tests/figures_and_makielayout.jl
Original file line number Diff line number Diff line change
Expand Up @@ -179,7 +179,6 @@ end
thetaticklabelsize = 18, thetaticklabelcolor = :blue,
thetaticklabelstrokewidth = 1, thetaticklabelstrokecolor = :white,
)

f
end

Expand All @@ -192,3 +191,36 @@ end
end
f
end

@reference_test "Colorbar for recipes" begin
fig, ax, pl = barplot(1:3; color=1:3, colormap=Makie.Categorical(:viridis), figure=(;resolution=(800, 800)))
Colorbar(fig[1, 2], pl; size=100)
x = LinRange(-1, 1, 20)
y = LinRange(-1, 1, 20)
z = LinRange(-1, 1, 20)
values = [sin(x[i]) * cos(y[j]) * sin(z[k]) for i in 1:20, j in 1:20, k in 1:20]

# TO not make this fail in CairoMakie, we dont actually plot the volume
_f, ax, cp = contour(x, y, z, values; levels=10, colormap=:viridis)
Colorbar(fig[2, :], cp; size=300)

# horizontal colorbars
Colorbar(fig[1, 3][2, 1]; limits=(0, 10), colormap=:viridis,
vertical=false)
Colorbar(fig[1, 3][3, 1]; limits=(0, 5), size=25,
colormap=cgrad(:Spectral, 5; categorical=true), vertical=false)
Colorbar(fig[1, 3][4, 1]; limits=(-1, 1), colormap=:heat, vertical=false, flipaxis=false,
highclip=:cyan, lowclip=:red)
xs = LinRange(0, 20, 50)
ys = LinRange(0, 15, 50)
zs = [cos(x) * sin(y) for x in xs, y in ys]
ax, hm = contourf(fig[2, 3][1, 1], xs, ys, zs;
colormap=:Spectral, levels=[-1, -0.5, -0.25, 0, 0.25, 0.5, 1])
Colorbar(fig[2, 3][1, 2], hm; ticks=-1:0.25:1)

ax, hm = contourf(fig[3, :][1, 1], xs, ys, zs;
colormap=:Spectral, colorscale=sqrt, levels=[ 0, 0.25, 0.5, 1])
Colorbar(fig[3, :][1, 2], hm; width=200)

fig
end
2 changes: 1 addition & 1 deletion WGLMakie/src/meshes.jl
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ function handle_color!(plot, uniforms, buffers, uniform_color_name = :uniform_co
uniforms[uniform_color_name] = Sampler(convert_text(color); minfilter=minfilter)
elseif color[] isa AbstractMatrix
uniforms[uniform_color_name] = Sampler(convert_text(color); minfilter=minfilter)
elseif color[] isa Makie.ColorMap
elseif color[] isa Makie.ColorMapping
if color[].color_scaled[] isa AbstractVector
buffers[:color] = Buffer(color[].color_scaled)
else
Expand Down
3 changes: 3 additions & 0 deletions docs/Project.toml
Original file line number Diff line number Diff line change
Expand Up @@ -27,3 +27,6 @@ Observables = "510215fc-4207-5dde-b226-833fc4488ee2"
RPRMakie = "22d9f318-5e34-4b44-b769-6e3734a732a6"
RadeonProRender = "27029320-176d-4a42-b57d-56729d2ad457"
WGLMakie = "276b4fcb-3e11-5398-bf8b-a0c2d153d008"

[compat]
Documenter = "<1"
5 changes: 1 addition & 4 deletions docs/reference/blocks/colorbar.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@


# Colorbar

A Colorbar needs a colormap and a tuple of low/high limits.
Expand Down Expand Up @@ -67,7 +65,6 @@ fig
```
\end{examplefigure}


## Attributes

\attrdocs{Colorbar}
\attrdocs{Colorbar}
1 change: 0 additions & 1 deletion docs/reference/plots/hexbin.md
Original file line number Diff line number Diff line change
Expand Up @@ -198,7 +198,6 @@ tightlimits!(ax)

Colorbar(f[1, 2], hb,
label = "Number of airports",
ticks = (0:3, ["0", "10", "100", "1000"]),
height = Relative(0.5)
)
f
Expand Down
12 changes: 3 additions & 9 deletions src/basic_recipes/contourf.jl
Original file line number Diff line number Diff line change
Expand Up @@ -48,9 +48,7 @@ end
# _computed_extendlow
# _computed_extendhigh

function _get_isoband_levels(levels::Int, mi, ma)
edges = Float32.(LinRange(mi, ma, levels+1))
end
_get_isoband_levels(levels::Int, mi, ma) = Float32.(LinRange(mi, ma, levels+1))

function _get_isoband_levels(levels::AbstractVector{<:Real}, mi, ma)
edges = Float32.(levels)
Expand All @@ -61,15 +59,14 @@ end
conversion_trait(::Type{<:Contourf}) = VertexBasedGrid()

function _get_isoband_levels(::Val{:normal}, levels, values)
_get_isoband_levels(levels, extrema_nan(values)...)
return _get_isoband_levels(levels, extrema_nan(values)...)
end

function _get_isoband_levels(::Val{:relative}, levels::AbstractVector, values)
mi, ma = extrema_nan(values)
Float32.(levels .* (ma - mi) .+ mi)
return Float32.(levels .* (ma - mi) .+ mi)
end


function Makie.plot!(c::Contourf{<:Tuple{<:AbstractVector{<:Real}, <:AbstractVector{<:Real}, <:AbstractMatrix{<:Real}}})
xs, ys, zs = c[1:3]

Expand All @@ -93,7 +90,6 @@ function Makie.plot!(c::Contourf{<:Tuple{<:AbstractVector{<:Real}, <:AbstractVec
map!(compute_highcolor, c, highcolor, c.extendhigh, c.colormap)
c.attributes[:_computed_extendhigh] = highcolor
is_extended_high = lift(!isnothing, c, highcolor)

PolyType = typeof(Polygon(Point2f[], [Point2f[]]))

polys = Observable(PolyType[])
Expand Down Expand Up @@ -161,9 +157,7 @@ inner polygons which are holes in the outer polygon. It is possible that one
group has multiple outer polygons with multiple holes each.
"""
function _group_polys(points, ids)

polys = [points[ids .== i] for i in unique(ids)]
npolys = length(polys)

polys_lastdouble = [push!(p, first(p)) for p in polys]

Expand Down
125 changes: 90 additions & 35 deletions src/colorsampler.jl
Original file line number Diff line number Diff line change
Expand Up @@ -176,88 +176,143 @@ function numbers_to_colors(numbers::Union{AbstractArray{<:Number, N},Number},
end
end

struct ColorMap{N,T<:AbstractArray{<:Number,N},T2<:AbstractArray{<:Number,N}}
"""
ColorMappingType
* categorical: there are n categories, and n colors are assigned to each category
* banded: there are ranges edge_start..edge_end, inside which values are mapped to one color
* continous: colors are mapped continuously to values
"""
@enum ColorMappingType categorical banded continuous


struct ColorMapping{N,T<:AbstractArray{<:Number,N},T2<:AbstractArray{<:Number,N}}
# The pure color values from the plot this colormapping is associated to
# Will be always an array of numbers
color::Observable{T}
colormap::Observable{Vector{RGBAf}}
scale::Observable{Union{ReversibleScale, Function}}
raw_colormap::Observable{Vector{RGBAf}} # the above is scaled (when coming from cgrad), this is not

# Scaling function that gets applied to color
scale::Observable{Function}

# The 0-1 scaled values from crange, which describe the colormapping
mapping::Observable{Union{Nothing, Vector{Float64}}}
colorrange::Observable{Vec{2,Float64}}

lowclip::Observable{Union{Automatic, RGBAf}} # Defaults to first color in colormap
highclip::Observable{Union{Automatic, RGBAf}} # Defaults to last color in colormap
nan_color::Observable{RGBAf}

categorical::Observable{Bool}
color_mapping_type::Observable{ColorMappingType}

# scaled attributes
colorrange_scaled::Observable{Vec2f}
color_scaled::Observable{T2}
end

function assemble_colors(::T, @nospecialize(color), @nospecialize(plot)) where {N, T<:AbstractArray{<:Number, N}}
color_tight = convert(Observable{T}, color)
colormap = Observable(RGBAf[]; ignore_equal_values=true)
categorical = Observable(false)
colorscale = convert(Observable{Union{ReversibleScale, Function}}, plot.colorscale)
mapping = Observable{Union{Nothing, Vector{Float64}}}(nothing)
struct Categorical{T} <: AbstractVector{RGBAf}
values::Vector{T}
end
Categorical(values) = Categorical(to_colormap(values))
Base.getindex(c::Categorical, i) = c.values[i]
Base.size(c::Categorical) = size(c.values)

_array_value_type(::Categorical{T}) where T = Vector{T}
_array_value_type(A::AbstractArray{<:Number}) = typeof(A)
_array_value_type(r::AbstractRange) = Vector{eltype(r)} # use vector instead, to have a few less types to worry about

_to_colormap(x::PlotUtils.ColorGradient) = to_colormap(x.colors)
_to_colormap(x) = to_colormap(x)


colormapping_type(@nospecialize(colormap)) = continuous
colormapping_type(::PlotUtils.CategoricalColorGradient) = banded
colormapping_type(::Categorical) = categorical

function ColorMapping(
color::AbstractArray{<:Number, N}, colors_obs, colormap, colorrange,
colorscale, alpha, lowclip, highclip, nan_color,
color_mapping_type=lift(colormapping_type, colormap; ignore_equal_values=true)) where {N}

T = _array_value_type(color)
color_tight = convert(Observable{T}, colors_obs)
map_colors = Observable(RGBAf[]; ignore_equal_values=true)
raw_colormap = Observable(RGBAf[]; ignore_equal_values=true)
mapping = Observable{Union{Nothing,Vector{Float64}}}(nothing; ignore_equal_values=true)
colorscale = convert(Observable{Function}, colorscale)

function update_colors(cmap, a)
colors = to_colormap(cmap)
raw_colors = _to_colormap(cmap) # dont do the scaling from cgrad
if a < 1.0
colors = map(c -> RGBAf(Colors.color(c), alpha(c) * a), colors)
colors = map(c -> RGBAf(Colors.color(c), Colors.alpha(c) * a), colors)
raw_colors = map(c -> RGBAf(Colors.color(c), Colors.alpha(c) * a), raw_colors)
end
colormap[] = colors
categorical[] = cmap isa PlotUtils.CategoricalColorGradient
if colormap isa PlotUtils.ColorGradient
map_colors[] = colors
raw_colormap[] = raw_colors
if cmap isa PlotUtils.ColorGradient
mapping[] = cmap.values
end
return
end
onany(update_colors, plot, plot.colormap, plot.alpha)
update_colors(plot.colormap[], plot.alpha[])

lowclip = Observable{Union{Automatic,RGBAf}}(automatic; ignore_equal_values=true)
on(plot, plot.lowclip; update=true) do lc
lowclip[] = lc isa Automatic ? lc : to_color(lc)
onany(update_colors, colormap, alpha)
update_colors(colormap[], alpha[])

_lowclip = Observable{Union{Automatic,RGBAf}}(automatic; ignore_equal_values=true)
on(lowclip; update=true) do lc
_lowclip[] = lc isa Union{Nothing, Automatic} ? automatic : to_color(lc)
return
end
highclip = Observable{Union{Automatic,RGBAf}}(automatic; ignore_equal_values=true)
on(plot, plot.highclip; update=true) do hc
highclip[] = hc isa Automatic ? hc : to_color(hc)
_highclip = Observable{Union{Automatic,RGBAf}}(automatic; ignore_equal_values=true)
on(highclip; update=true) do hc
_highclip[] = hc isa Union{Nothing,Automatic} ? automatic : to_color(hc)
return
end
nan_color = lift(to_color, plot.nan_color)
colorrange = Observable(Vec{2, Float64}(0); ignore_equal_values=true)

colorrange = lift(color_tight, plot.colorrange; ignore_equal_values=true) do color, crange
colorrange = lift(color_tight, colorrange; ignore_equal_values=true) do color, crange
return crange isa Automatic ? Vec2{Float64}(distinct_extrema_nan(color)) : Vec2{Float64}(crange)
end

colorrange_scaled = lift(colorrange, colorscale; ignore_equal_values=true) do range, scale
return Vec2f(apply_scale(scale, range))
end

color_scaled = lift(color_tight, colorscale) do color, scale
return el32convert(apply_scale(scale, color))
end
return ColorMap{N, T, typeof(color_scaled[])}(
CT = ColorMapping{N,T,typeof(color_scaled[])}

return CT(
color_tight,
colormap,
map_colors,
raw_colormap,
colorscale,
mapping,
colorrange,
lowclip,
highclip,
nan_color,
categorical,
_lowclip,
_highclip,
lift(to_color, nan_color),
color_mapping_type,
colorrange_scaled,
color_scaled
)
color_scaled)
end

function assemble_colors(c::AbstractArray{<:Number}, @nospecialize(color), @nospecialize(plot))
return ColorMapping(c, color, plot.colormap, plot.colorrange, plot.colorscale, plot.alpha, plot.lowclip,
plot.highclip, plot.nan_color)
end

function to_color(c::ColorMap)
function to_color(c::ColorMapping)
return numbers_to_colors(c.color_scaled[], c.colormap[], identity, c.colorrange_scaled[], lowclip(c)[], highclip(c)[], c.nan_color[])
end

function Base.get(c::ColorMapping, value::Number)
return numbers_to_colors([value], c.colormap[], c.scale[], c.colorrange_scaled[], lowclip(c)[],
highclip(c)[], c.nan_color[])[1]
end

function assemble_colors(colortype, color, plot)
return lift(plot, color, plot.alpha) do color, a
if a < 1.0
Expand All @@ -276,5 +331,5 @@ function assemble_colors(::Number, color, plot)
cm.nan_color)
end

highclip(cmap::ColorMap) = lift((cm, hc) -> hc isa Automatic ? last(cm) : hc, cmap.colormap, cmap.highclip)
lowclip(cmap::ColorMap) = lift((cm, hc) -> hc isa Automatic ? first(cm) : hc, cmap.colormap, cmap.lowclip)
highclip(cmap::ColorMapping) = lift((cm, hc) -> hc isa Automatic ? last(cm) : hc, cmap.colormap, cmap.highclip)
lowclip(cmap::ColorMapping) = lift((cm, hc) -> hc isa Automatic ? first(cm) : hc, cmap.colormap, cmap.lowclip)
2 changes: 1 addition & 1 deletion src/interaction/inspector.jl
Original file line number Diff line number Diff line change
Expand Up @@ -219,7 +219,7 @@ disable!(inspector::DataInspector) = inspector.attributes.enabled[] = false
Creates a data inspector which will show relevant information in a tooltip
when you hover over a plot.
This functionality can eb disabled on a per-plot basis by setting
This functionality can be disabled on a per-plot basis by setting
`plot.inspectable[] = false`. The displayed text can be adjusted by setting
`plot.inspector_label` to a function `(plot, index, position) -> "my_label"`
returning a label. See Makie documentation for more detail.
Expand Down
5 changes: 3 additions & 2 deletions src/layouting/transformation.jl
Original file line number Diff line number Diff line change
Expand Up @@ -330,7 +330,8 @@ apply_transform(f::NTuple{3, typeof(identity)}, r::Rect) = r
const pseudolog10 = ReversibleScale(
x -> sign(x) * log10(abs(x) + 1),
x -> sign(x) * (exp10(abs(x)) - 1);
limits=(0f0, 3f0)
limits=(0f0, 3f0),
name=:pseudolog10
)

Symlog10(hi) = Symlog10(-hi, hi)
Expand All @@ -351,7 +352,7 @@ function Symlog10(lo, hi)
else
x
end
ReversibleScale(forward, inverse; limits=(0f0, 3f0))
return ReversibleScale(forward, inverse; limits=(0.0f0, 3.0f0), name=:Symlog10)
end

inverse_transform(::typeof(identity)) = identity
Expand Down
Loading

0 comments on commit d4f6ce8

Please sign in to comment.