Reputation: 915
I'm trying to display a plot in a shiny app with specific height and width dimensions and specific font size/family but when it renders in the app, the png seems to be very low resolution. If I try to change the res
value it makes the plot being displayed larger (which is not what I want). Is there a way to increase the resolution/dpi of the plot without changing its size?
Optimally, I would want to be able to zoom in on the webpage without having the plot look blurry. Is this possible with a png? Would I need to display the plot using something other than renderPlot
?
library(shiny)
# Define UI for app that draws a histogram ----
ui <- fluidPage(
# App title ----
titlePanel("Hello Shiny!"),
mainPanel(
plotOutput(outputId = "Plot", width = "auto", height = "auto")
)
)
# Define server logic required to draw a histogram ----
server <- function(input, output, session) {
output$Plot <- renderPlot({
ggplot(iris, aes(x = Sepal.Length, y = Sepal.Width)) +
geom_point() +
theme(
line = element_line(
colour = "black",
size = 0.25
),
text = element_text(
family = "Helvetica",
size = 9,
colour = "black"
),
rect = element_blank(),
panel.grid = element_blank(),
legend.position = "top",
legend.title = element_text(
family = "Helvetica",
size = 9,
colour = "black"
),
legend.text = element_text(
family = "Helvetica",
size = 9,
colour = "black"
),
# axis.line = element_line(colour = "black", size = stroke),
axis.line.x = element_line(colour = "black", size = 0.25),
axis.line.y = element_line(colour = "black", size = 0.25),
axis.ticks.x = element_blank(),
axis.text.x = element_text(
family = "Helvetica",
size = 9,
colour = "black"
),
axis.text = element_text(
family = "Helvetica",
size = 9,
colour = "black"
),
plot.margin = margin(5, 5, 5, 5, "mm"),
legend.margin = margin(0, 0, 0, 0, "mm")
)
}, height = 200, width = 200)
}
shinyApp(ui, server)
Upvotes: 7
Views: 3234
Reputation: 915
I found a workaround using renderImage() which allows you to store a temporary .png file that is larger with higher resolution and then you can display it on the page at a smaller size which seems to preserve the higher resolution.
You may need to zoom in with your browser to appreciate the difference but it helped quite a bit!
library(shiny)
# Define UI for app that draws a histogram ----
ui <- fluidPage(
titlePanel("Hello Shiny!"),
mainPanel(
h3("Low resolution"),
plotOutput(outputId = "Plot", width = "auto", height = "auto"),
hr(),
h3("High resolution"),
imageOutput("myImage", height = "100%", width = "100%")
)
)
# Define server logic required to draw a histogram ----
server <- function(input, output, session) {
Plot <- ggplot(iris, aes(x = Sepal.Length, y = Sepal.Width)) +
geom_point()
output$Plot <- renderPlot({
Plot
}, height = 200, width = 200)
# Plot the data ####
output$myImage <- renderImage({
# A temp file to save the output.
# This file will be removed later by renderImage
outfile <- tempfile(fileext = '.png')
# Generate the PNG
png(outfile,
width = 200*8,
height = 200*8,
res = 72*8)
print(Plot)
dev.off()
# Return a list containing the filename
list(src = outfile,
contentType = 'image/png',
width = 200,
height = 200,
alt = "This is alternate text")
}, deleteFile = TRUE)
}
shinyApp(ui, server)
Upvotes: 7