Skip to content

Instantly share code, notes, and snippets.

@ttnsy
Forked from Gotfrid/searchable_dropdown.R
Last active December 11, 2023 10:11
Show Gist options
  • Save ttnsy/00ccb5978ec8dfe665440c5158cd628c to your computer and use it in GitHub Desktop.
Save ttnsy/00ccb5978ec8dfe665440c5158cd628c to your computer and use it in GitHub Desktop.
shiny.fluent Dropdown component with search capabilities
#' shiny.fluent[0.2.1]
box::use(
shiny[div, moduleServer, NS, observeEvent],
shiny.fluent[JS, fluentPage, Dropdown.shinyInput]
)
DropdownMenuItemType <- function(type) { # nolint
JS(paste0("jsmodule['@fluentui/react'].DropdownMenuItemType."), type)
}
options_with_search <- function(opt) {
filter_header <- list(
key = "__FilterHeader__",
text = "-",
itemType = DropdownMenuItemType("Header")
)
append(list(filter_header), opt)
}
SearchableDropdown <- function(id, opt, ...) {
render_search_box <- JS(paste0("(option) => {
if (option.key !== '__FilterHeader__') {
return option.text;
}
const onChange = (event, newValue) => {
const query = newValue.toLocaleLowerCase();
const checkboxLabels = document.querySelectorAll(
'#", id, "-list .ms-Checkbox-label'
);
checkboxLabels.forEach(label => {
const text = label.innerText.replace('\\n', '').replace('', '').toLocaleLowerCase();
if (query === '' || text.startsWith(query)) {
label.parentElement.style.display = 'flex';
} else {
label.parentElement.style.display = 'none';
}
});
};
const props = { placeholder: 'Start typing', underlined: true, onChange };
const element = React.createElement(jsmodule['@fluentui/react'].SearchBox, props)
return element;
}"))
Dropdown.shinyInput(
inputId = id,
multiSelect = TRUE,
placeholder = "Fruit/Vegetable",
options = options_with_search(opt),
...,
onRenderOption = render_search_box
)
}
#' @export
ui <- function(id) {
ns <- NS(id)
fluentPage(
div(
style = "height: 100%; width: 50%; margin:auto",
SearchableDropdown(
id = "fruit",
label = "Searchable Fruit Selector",
opt = list(
list(key = "apple", text = "Apple"),
list(key = "banana", text = "Banana"),
list(key = "orange", text = "Orange"),
list(key = "grape", text = "Grape"),
list(key = "broccoli", text = "Broccoli"),
list(key = "carrot", text = "Carrot"),
list(key = "lettuce", text = "Lettuce")
)
)
)
)
}
#' @export
server <- function(id) {
moduleServer(id, function(input, output, session) {
observeEvent(input$fruit, {
print(input$fruit)
})
})
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment