-
Notifications
You must be signed in to change notification settings - Fork 12
Description
This package defines Base.displayable for the ::TerminalGraphicDisplay with MIME image/png:
ImageInTerminal.jl/src/display.jl
Lines 7 to 11 in 6d2390b
| Base.displayable(::TerminalGraphicDisplay, ::MIME"image/png", x::Any) = | |
| showable("image/png", x) | |
| Base.displayable(::TerminalGraphicDisplay, ::MIME"image/png", ::Vector{UInt8}) = true | |
| Base.displayable(::TerminalGraphicDisplay, ::MIME"image/png", ::AbstractArray{<:Colorant}) = | |
| true |
The README mentions rendering for Colorant and for Latexify.jl, but we can also use it in a third-party package MyPackage to render custom types in form of an image if ImageInTerminal is loaded. For example:
module MyPackage
import Sixel
const SIXEL_SUPPORTED = Ref(false)
struct MyType end
# Base.summary(io::IO, x::MyType) = ...
function Base.show(io::IO, ::MIME"text/plain", x::MyType)
println(io, summary(x), ":")
# only render as image if terminal has Sixel support
if SIXEL_SUPPORTED[] && displayable("image/png")
display("image/png", x)
else
# println(...)
end
end
function Base.show(io::IO, ::MIME"image/png", x::MyType)
# ...
end
__init__() = SIXEL_SUPPORTED[] = Sixel.is_sixel_supported()
endHowever, ImageInTerminal also defines functions disable_encoding() and enable_encoding() to toggle image rendering on/off during runtime. Currently there is no way for MyPackage to know whether the user has toggled image rendering, and therefore calling ImageInTerminal.disable_encoding() has no effect for the code shown above. I wonder whether the current state should be reflected in displayable, like this (here only the first line seems relevant for third-party packages):
Base.displayable(::TerminalGraphicDisplay, ::MIME"image/png", x::Any) = SHOULD_RENDER_IMAGE[] && showable("image/png", x)
Base.displayable(::TerminalGraphicDisplay, ::MIME"image/png", ::Vector{UInt8}) = SHOULD_RENDER_IMAGE[]
Base.displayable(::TerminalGraphicDisplay, ::MIME"image/png", ::AbstractArray{<:Colorant}) = SHOULD_RENDER_IMAGE[]What do you think?
Edit: Actually I just realized that in the code above I call only displayable("image/png"), without the x::MyType, and the solution suggested here doesn't work. I'll try to find out where the single-argument displayable comes from and how it relates to the methods that are defined in this package (loading ImageInTerminal does have an effect for the single-argument displayable("image/png")).
Edit 2: Okay, I found it at https://github.com/JuliaLang/julia/blob/3076a9683609b5c587ae3cbc70b25b7332018c7f/base/multimedia.jl#L364-L372
In particular displayable("image/png") only checks if there is a method display("image/png", x::Any) defined for any display in the display stack. Indeed it is defined at
ImageInTerminal.jl/src/display.jl
Line 13 in 6d2390b
| function Base.display(d::TerminalGraphicDisplay, ::MIME"image/png", x::Any) |
This means that
displayable("image/png") will unconditionally always return true if ImageInTerminal is loaded, and I will need to think of another way how the ImageInTerminal.disable_encoding() could propagate to third-party packages.