Skip to content

Commit c787e8a

Browse files
authored
parameters with choices and multiple = TRUE should use a select input (#2576)
1 parent 9bf0910 commit c787e8a

File tree

3 files changed

+108
-6
lines changed

3 files changed

+108
-6
lines changed

NEWS.md

+21
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,27 @@ rmarkdown 2.29
33

44
- `find_external_resources()` now correctly detects knitr child document provided with option like `child = c("child.Rmd")` (thanks, @rempsyc, #2574).
55

6+
- `knit_params_ask()` uses a `select` input for parameters which allow multiple selected values. Previously, a `radio` input was incorrectly used when the parameter had a small number of choices.
7+
8+
```yaml
9+
params:
10+
primaries:
11+
choices: ["red", "yellow", "blue"]
12+
multiple: true
13+
```
14+
15+
When `multiple` is not enabled, parameter configuration still uses `radio` when there are fewer than five choices.
16+
17+
The `input` parameter field can still be used to force the configuration control.
18+
19+
```yaml
20+
params:
21+
grade:
22+
input: radio
23+
choices: ["A", "B", "C", "D", "F"]
24+
```
25+
26+
627
rmarkdown 2.28
728
================================================================================
829

R/params.R

+7-6
Original file line numberDiff line numberDiff line change
@@ -161,11 +161,13 @@ params_get_input <- function(param) {
161161
input <- param$input
162162
if (is.null(input)) {
163163
if (!is.null(param$choices)) {
164-
## radio buttons for a small number of choices, select otherwise.
165-
if (length(param$choices) <= 4) {
166-
input <- "radio"
167-
} else {
164+
## select for a large number of choices and multiple choices.
165+
if (isTRUE(param$multiple)) {
166+
input <- "select"
167+
} else if (length(param$choices) > 4) {
168168
input <- "select"
169+
} else {
170+
input <- "radio"
169171
}
170172
} else {
171173
## Not choices. Look at the value type to find what input control we
@@ -219,8 +221,7 @@ params_configurable <- function(param) {
219221
}
220222
# Some inputs (like selectInput) support the selection of
221223
# multiple entries through a "multiple" argument.
222-
multiple_ok <- (!is.null(param$multiple) && param$multiple)
223-
if (multiple_ok) {
224+
if (isTRUE(param$multiple)) {
224225
return(TRUE)
225226
}
226227
# sliderInput supports either one or two-value inputs.

tests/testthat/test-params.R

+80
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,86 @@ test_that("parameters are configurable", {
105105
value = c(10, 20, 30))))
106106
})
107107

108+
test_that("params_get_input", {
109+
# input derived from value type.
110+
expect_equal(params_get_input(list(
111+
value = TRUE
112+
)), "checkbox")
113+
expect_equal(params_get_input(list(
114+
value = as.integer(42)
115+
)), "numeric")
116+
expect_equal(params_get_input(list(
117+
value = 7.5
118+
)), "numeric")
119+
expect_equal(params_get_input(list(
120+
value = "character"
121+
)), "text")
122+
expect_equal(params_get_input(list(
123+
value = Sys.Date()
124+
)), "date")
125+
expect_equal(params_get_input(list(
126+
value = Sys.time()
127+
)), "datetime")
128+
129+
# numeric becomes a slider with both min and max
130+
expect_equal(params_get_input(list(
131+
value = as.integer(42),
132+
min = 0
133+
)), "numeric")
134+
expect_equal(params_get_input(list(
135+
value = as.integer(42),
136+
max = 100
137+
)), "numeric")
138+
expect_equal(params_get_input(list(
139+
value = as.integer(42),
140+
min = 0,
141+
max = 100
142+
)), "slider")
143+
expect_equal(params_get_input(list(
144+
value = 7.5,
145+
min = 0
146+
)), "numeric")
147+
expect_equal(params_get_input(list(
148+
value = 7.5,
149+
max = 10
150+
)), "numeric")
151+
expect_equal(params_get_input(list(
152+
value = 7.5,
153+
min = 0,
154+
max = 10
155+
)), "slider")
156+
157+
# choices implies radio or select
158+
expect_equal(params_get_input(list(
159+
value = "red",
160+
choices = c("red", "green", "blue")
161+
)), "radio")
162+
expect_equal(params_get_input(list(
163+
value = "red",
164+
multiple = TRUE,
165+
choices = c("red", "green", "blue")
166+
)), "select")
167+
expect_equal(params_get_input(list(
168+
value = "red",
169+
choices = c("red", "green", "blue", "yellow", "black", "white")
170+
)), "select")
171+
expect_equal(params_get_input(list(
172+
value = "red",
173+
multiple = TRUE,
174+
choices = c("red", "green", "blue", "yellow", "black", "white")
175+
)), "select")
176+
177+
# explicit input overrides inference
178+
expect_equal(params_get_input(list(
179+
input = "slider",
180+
value = 42
181+
)), "slider")
182+
expect_equal(params_get_input(list(
183+
input = "file",
184+
value = "data.csv"
185+
)), "file")
186+
})
187+
108188
test_that("params hidden w/o show_default", {
109189

110190
# file input is always NULL

0 commit comments

Comments
 (0)