You are currently browsing Joe Cheng’s articles.

Leaflet 1.1.0 is now available on CRAN! The Leaflet package is a tidy wrapper for the Leaflet.js mapping library, and makes it incredibly easy to generate interactive maps based on spatial data you have in R.


This release was nearly a year in the making, and includes many important new features.

  • Easily add textual labels on markers, polygons, etc., either on hover or statically
  • Highlight polygons, lines, circles, and rectangles on hover
  • Markers can now be configured with a variety of colors and icons, via integration with Leaflet.awesome-markers
  • Built-in support for many types of objects from sf, a new way of representing spatial data in R (all basic sf/sfc/sfg types except MULTIPOINT and GEOMETRYCOLLECTION are directly supported)
  • Projections other than Web Mercator are now supported via Proj4Leaflet
  • Color palette functions now natively support viridis palettes; use "viridis", "magma", "inferno", or "plasma" as the palette argument
  • Discrete color palette functions (colorBin, colorQuantile, and colorFactor) work much better with color brewer palettes
  • Integration with several Leaflet.js utility plugins
  • Data with NA points or zero rows no longer causes errors
  • Support for linked brushing and filtering, via Crosstalk (more about this to come in another blog post)

Many thanks to @bhaskarvk who contributed much of the code for this release.

Going forward, our intention is to prevent any more Leaflet.js plugins from accreting in the core leaflet package. Instead, we have made it possible to write 3rd party R packages that extend leaflet (though the process to do this is not documented yet). In the meantime, Bhaskar has started developing his own leaflet.extras package; it already supports several plugins, for everything from animated markers to heatmaps.

Shiny Server and Shiny Server Pro are now available.

The Shiny Server 1.5.x release family upgrades our underlying Node.js engine from 0.10.47 to 6.9.1. The impetus for this change was not stability or performance, but because the 0.10.x release family has reached the end of its life.

We highly recommend that you test on a staging server before upgrading production Shiny Server 1.4.x machines to 1.5. You should always do this for any production-critical software, but it’s particularly important for this release, due to the magnitude of changes to Node.js that we’ve absorbed in one big gulp. (We’ve done thorough end-to-end testing of this release, but there’s no substitute for testing with your own apps, on your own servers.)

Some small bug fixes are also included in this release. See the release notes for more details.

The beginning of the end for Ubuntu 12.04 and Red Hat 5

While we still support Ubuntu 12.04 and Red Hat 5 today, we’ll be moving on from these very old releases in a few months. Both of these distributions will end-of-life in April 2017, and will stop receiving bug fixes and security fixes from their vendors at that time. If you’re using Shiny Server with one of these platforms, we recommend that you start planning your upgrade.

Shiny Server and Shiny Server Pro are now available! This release includes new features to support Shiny 0.14. It also updates our Node.js to 0.10.47, which includes important security fixes for SSL/TLS.

Connection robustness (a.k.a. grey-outs)

Shiny’s architecture is built on top of websockets, which are long-lived network connections between the browser and an R session on the server. If this connection is broken for any reason, the browser is no longer able to communicate with its R session on the server. Shiny indicates this to the user by turning the page background grey and fading out the page contents.

In Shiny 0.14 and Shiny Server 1.4.7, we’ve done work at both the server and package levels to minimize the amount of greyouts users will see. Simply by upgrading Shiny Server, transient (<15sec) network interruptions should no longer disrupt Shiny apps. And for many Shiny apps, a secondary, opt-in reconnection mechanism should all but eliminate grey-outs. This article on has all the details.

Bookmarkable state

Shiny 0.14 introduced a “bookmarkable state” feature that made it possible to snapshot the state of a running Shiny app, and send it to someone as a URL to try in their own browser. At the app author’s option, the app state could either be fully encoded in the URL, or written to disk and referred to by a short ID. This latter approach requires support from the server, and that support is now officially provided by Shiny Server and Shiny Server 1.4.7. (This functionality is not yet available for, however.)

Coming soon: Shiny Server 1.5.0

Just a heads up: Shiny Server (Pro) 1.5.0 is coming in a few weeks. Shiny Server was originally written using Node.js 0.10, which is nearing the end of its lifespan. This release will move to Node.js 6.x.

Due to the complexity of this upgrade, Shiny Server 1.5.0 will not add any new features, except for supporting perfect forward secrecy for SSL/TLS connections. The focus will be entirely on ensuring a smooth and stable release.

We’ve just released Shiny Server and Shiny Server Pro 1.4.6. Relative to 1.4.2, our previously blogged-about version, the 1.4.6 release primarily includes bug fixes, and mitigations for low-severity security issues found by penetration testing. The full list of changes is after the jump.

If you’re running a Shiny Server Pro release that is older than 1.4.3 and are configured to use SSL/TLS, it’s especially important that you upgrade, as the versions of Node.js that are bundled with Shiny Server Pro 1.4.3 and earlier include vulnerable versions of OpenSSL.

Shiny Server (Open Source): Download now

Shiny Server Pro: If you already have a license or evaluation key, please upgrade now. Otherwise, you can start a free 45-day evaluation.

Read the rest of this entry »

This past January, we held the first ever Shiny Developer Conference. It was a chance to gather together a group of intermediate to advanced Shiny users, and take their skills to the next level.

It was an exciting event for me in particular, as I’ve been dying to share some of these intermediate and advanced Shiny concepts for years now. There are many concepts that aren’t strictly required to be productive with Shiny, but make a huge difference in helping you write efficient, robust, maintainable apps—and also make Shiny app authoring a lot more satisfying.

The feedback we received from conference attendees was overwhelmingly positive: everyone from relative novices to the most advanced users told us they gained new insights into how to improve their Shiny apps, or had a perspective shift on concepts they thought they already understood. The user-contributed lightning talks were also a big hit, helping people see what’s possible using Shiny and inspiring them to push their own apps further.

If you weren’t able to attend but are still interested in building your Shiny skills, we’re happy to announce the availability of videos of the tutorials and talks:

Shiny Developer Conference 2016 Videos

At the moment, these videos are our best sources of info on the topics of reactive programming, Shiny gadgets, Shiny modules, debugging Shiny apps, and performance. If you’re at all serious about writing Shiny apps, we highly recommend you take the time to watch!

If you’re interested in attending next year’s conference, you can sign up for our email list using the subscription form at the top of the Shiny Developer Conference 2016 Videos page, and we’ll let you know when more details are available.

Update Nov 2 2015: Wow, that was fast. Registration is full. If you add yourself to the waitlist, we’ll contact you first if/when we do this conference again.

In the three years since we launched Shiny, our focus has been on helping people get started with Shiny. But there’s a huge difference between using Shiny and using it well, and we want to start getting serious about helping people use Shiny most effectively. It’s the difference between having apps that merely work, and apps that are performant, robust, and maintainable.

That’s why RStudio is thrilled to announce the first ever Shiny Developer Conference, to be held at Stanford University on January 30-31, 2016, three months from today. We’ll skip past the basics, and dig into principles and practices that will simultaneously simplify and improve the robustness of your code. We’ll introduce you to some brand new tools we’ve created to help you build ever larger and more complex apps. And we’ll show you what to do if things go wrong.

Check out the agenda to see the complete lineup of speakers and talks.

We’re capping the conference at just 90 people, so if you’d like to level up your Shiny skills, register now at

Hope to see you there!

Note that this conference is intended for R users who are already comfortable writing Shiny apps. We won’t cover the basics of Shiny app creation at all. If you’re looking to get started with Shiny, please see our tutorial.

We’re pleased to announce d3heatmap, our new package for generating interactive heat maps using d3.js and htmlwidgets. Tal Galili, author of dendextend, collaborated with us on this package.

d3heatmap is designed to have a familiar feature set and API for anyone who has used heatmap or heatmap.2 to create static heatmaps. You can specify dendrogram, clustering, and scaling options in the same way.

d3heatmap includes the following features:

  • Shows the row/column/value under the mouse cursor
  • Click row/column labels to highlight
  • Drag a rectangle over the image to zoom in
  • Works from the R console, in RStudio, with R Markdown, and with Shiny




Here’s a very simple example (source: flowingdata):

url <- ""
nba_players <- read.csv(url, row.names = 1)
d3heatmap(nba_players, scale = "column")


You can easily customize the colors using the colors parameter. This can take an RColorBrewer palette name, a vector of colors, or a function that takes (potentially scaled) data points as input and returns colors.

Read the rest of this entry »

Shiny 0.12 has been released to CRAN!

Compared to version 0.11.1, the major changes are:

  • Interactive plots with base graphics and ggplot2
  • Switch from RJSONIO to jsonlite

For a full list of changes and bugfixes in this version, see the NEWS file.

To install the new version of Shiny, run:

install.packages(c("shiny", "htmlwidgets"))

htmlwidgets is not required, but shiny 0.12 will not work with older versions of htmlwidgets, so it’s a good idea to install a fresh copy along with Shiny.

Interactive plots with base graphics and ggplot2

Excluding points

The major new feature in this version of Shiny is the ability to create interactive plots using R’s base graphics or ggplot2. Adding interactivity is easy: it just requires using one option in plotOutput(), and then the information about mouse events will be available via the input object.

You can use mouse events to read mouse coordinates, select or deselect points, and implement zooming. Here are some example applications:

For more information, see the Interactive Plots articles in the Shiny Dev Center, and the demo apps in the gallery.

Switch from RJSONIO to jsonlite

Shiny uses the JSON format to send data between the server (running R) and the client web browser (running JavaScript).

In previous versions of Shiny, the data was serialized to/from JSON using the RJSONIO package. However, as of 0.12.0, Shiny switched from RJSONIO to jsonlite. The reasons for this are that jsonlite has better-defined conversion behavior, and it has better performance because much of it is now implemented in C.

For the vast majority of users, this will have no impact on existing Shiny apps.

The htmlwidgets package has also switched to jsonlite, and any Shiny apps that use htmlwidgets also require an upgrade to that package.

A note about Data Tables

The version we just released to CRAN is actually 0.12.1; the previous version, 0.12.0, was released three weeks ago and deprecated Shiny’s dataTableOutput and renderDataTable functions and instructed you to migrate to the nascent DT package instead. (We’ll talk more about DT in a future blog post.)

User feedback has indicated this transition was too sudden and abrupt, so we’ve undeprecated these functions in 0.12.1. We’ll continue to support these functions until DT has had more time to mature.

Shiny 0.10 is now available on CRAN.

Interactive documents

In this release, the biggest changes were under the hood to support the creation of interactive documents. If you haven’t had a chance to check out interactive documents, we really encourage you to do so—it may be the easiest way to learn Shiny.

New layout functions

Three new functions—flowLayout(), splitLayout(), and inputPanel()—were added for putting UI elements side by side.

  • flowPanel() lays out its children in a left-to-right, top-to-bottom arrangement.
  • splitLayout() evenly divides its horizontal space among its children (or unevenly divides if cellWidths argument is provided).
  • inputPanel() is like flowPanel(), but with a light grey background, and is intended for encapsulating small input controls wherever vertical space is at a premium.

A new logical argument inline was also added to checkboxGroupInput() and radioButtons() to arrange check boxes and radio buttons horizontally.

Custom validation error messages

Sometimes you don’t want your reactive expressions or output renderers in server.R to proceed unless certain input conditions are satisfied, e.g. a select input value has been chosen, or a sensible combination of inputs has been provided. In these cases, you might want to stop the render function quietly, or you might want to give the user a custom message. In shiny 0.10.0, we introduced the functions validate() and need() which you can use to enforce validation conditions. This won’t be the last word on input validation in Shiny, but it should be a lot safer and more convenient than how most of us have been doing it.

See the article Write error messages for your UI with validate for details and examples.

Sever-side processing for Selectize input

In the previous release of Shiny, we added support for Selectize, a powerful select box widget. At that time, our implementation passed all of the data to the web page and used JavaScript to do any paging, filtering, and sorting. It worked great for small numbers of items but didn’t scale well beyond a few thousand items.

For Shiny 0.10, we greatly improved the performance of our existing client-side Selectize binding, but also added a new mode that allows the paging, filtering, and sorting to all happen on the server. Only the results that are actually displayed are downloaded to the client. This approach works well for hundreds of thousands or millions of rows.

For more details and examples, see the article Using selectize input on


We also split off Shiny’s HTML generating library (tags and friends) into a separate htmltools package. If you’re writing a package that needs to generate HTML programmatically, it’s far easier and safer to use htmltools than to paste HTML strings together yourself. We’ll have more to share about htmltools in the months to come.

Other changes

  • New actionLink() input control: behaves like actionButton() but looks like a link
  • renderPlot() now calls print() on its result if it’s visible–no more explicit print() required for ggplot2
  • Sliders and select boxes now use a fixed horizontal size instead of filling up all available horizontal space; pass width="100%" if you need the old behavior
  • The session object that can be passed into a server function is now documented: see ?session
  • New reactive domains feature makes it easy to get callbacks when the current session ends, without having to pass session everywhere
  • Thanks to reactive domains, by default, observers now automatically stop executing when the Shiny session that created them ends
  • shinyUI and shinyServer

For the full list, you can take a look at the NEWS file. Please let us know if you have any comments or questions.

We’re excited to introduce to you our new website for Shiny:!


We’ve included articles on many Shiny-related topics, dozens of example applications, and an all-new tutorial for getting started.

Whether you’re a beginner or expert at Shiny, we hope that having these resources available in one place will help you find the information you need.

We’d also like to announce Shiny 0.9, now available on CRAN. This release includes many bug fixes and new features, including:

New application layout options

Until now, the vast majority of Shiny apps have used a sidebar-style layout. Shiny 0.9 introduces new layout features to:

  1. Make it easy to create custom page layouts using the Bootstrap grid system. See our new application layout guide or a live example.
  2. Provide navigation bars and lists for separating your application into different pages. See navbarPage and navlistPanel, and this example.
  3. Enhance tabsetPanel to allow pill-style tabs, and to let tabs be placed above, below, or to either side of tab content.
  4. Create floating panels and place them relative to the sides of the page, optionally making them draggable. See absolutePanel or this example.
  5. Use Bootstrap themes to easily modify the fonts and colors of your application. Example

You can see many of these features in action together in our reimplementation of the Washington Post’s interactive article on Super Zips.

Selectize.js integration

The JavaScript library selectize.js provides a much more flexible interface compared to the basic select input. It allows you to type and search in the options, use placeholders, control the number of options/items to show/select, and so on.


We have integrated selectize.js in shiny 0.9, and selectInput now creates selectize inputs by default. (You can revert back to plain select inputs by passing selectize=FALSE to selectInput.) For more advanced uses, we have included a new selectizeInput function that lets you pass options to selectize.

Please check out this example to see a subset of features of the selectize input. There is also an example comparing the select and selectize input.

Showcase mode

Shiny apps can now (optionally) run in a “showcase” mode in which the app’s R code can be automatically displayed within the app. Most of the Shiny example apps in our new gallery use showcase mode.

Showcase example

As you interact with the application, reactive expressions and outputs in server.R will light up as they execute. This can be helpful in visualizing the reactivity in your app.

See this article to learn more.

As always, you can install the latest release of Shiny by running this command at the R console:


The complete list of bug fixes and features is available in the NEWS file.

We hope you’ll find these new features helpful in exploring and understanding your data!