带有条件面板的闪亮仪表板中的动态菜单
Dynamic menu in shinydashboard with conditionalPanel
背景
我正在尝试开发一个应用程序,它有一个登录屏幕,并根据用户的权限显示不同的菜单。
用户权限是分层的,这意味着 Read + Write
用户应该拥有与 Read
用户相同的权限以及一些额外的权限。
我现在正在纠结如何创建这个动态菜单。我阅读了 this document on dynamic UIs,我希望我可以纯粹通过使用 conditionalPanel
调用来实现我的目标。
在下面的代码中,您会发现有很多重复项。最糟糕的是,我必须为 tabs
分配唯一的名称,即使它们位于不同的(互斥的)面板(a1
和 a2
)中,但它们的目的恰恰是一样。
到目前为止已经尝试过
我试图将 conditionalPanel
移动到 sidebarMenu
(和 tabItems
分别),但随后出现错误,因为 return 类型 conditionalPanel
与预期类型不匹配。
预期结果
最后,我希望代码重复最少。也就是说,我想为 Do A
和 Do B
定义 一次 ,但是 重新使用 Do A
两个用户。
我有哪些选择?我是否必须回退到动态渲染 (renderUI
/ renderMenu
) 或有什么方法可以仅使用 conditionalPanel
实现所需的行为?
有重复的工作代码
library(shiny)
library(shinydashboard)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(
selectInput("userrights", label = "User Rights:",
choices = c("Read + Write", "Read")),
conditionalPanel("input.userrights == 'Read'",
sidebarMenu(
menuItem("Do A", tabName = "a1")
)
),
conditionalPanel("input.userrights == 'Read + Write'",
sidebarMenu(
## unnecessary duplication + I need yet another tab 'a2'
menuItem("Do A", tabName = "a2"),
menuItem("Do B", tabName = "b2")
)
)
),
dashboardBody(
conditionalPanel("input.userrights == 'Read'",
tabItems(
tabItem("a1", h1("A was done"))
)
),
conditionalPanel("input.userrights == 'Read + Write'",
tabItems(
tabItem("a2", h1("A was done")),
tabItem("b2", h1("B was done"))
)
)
)
)
server <- function(input, output) {}
runApp(shinyApp(ui, server))
片段:不工作但至少 w/o 重复
sidebarMenu(
menuItem("Do A", tabName = "a")
conditionalPanel("input.userrights == 'Read + Write'",
menuItem("Do B", tabName = "b")
)
)
您可以根据用户输入或其他条件在服务器中呈现您的菜单,并将其输出到 UI。下面的工作示例:
library(shiny)
library(shinydashboard)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(
selectInput("userrights", label = "User Rights:",
choices = c("Read + Write", "Read")),
sidebarMenuOutput("menu")
),
dashboardBody(
tabItems(
tabItem("a", h1("A was done")),
tabItem("b", h1("B was done"))
)
)
)
server <- function(input, output) {
output$menu <- renderMenu({
my_list = list(menuItem("a", tabName="a"))
if(input$userrights=="Read + Write")
my_list[[2]] = menuItem("b", tabName="b")
sidebarMenu(my_list)
})
}
runApp(shinyApp(ui, server))
希望对您有所帮助!
背景
我正在尝试开发一个应用程序,它有一个登录屏幕,并根据用户的权限显示不同的菜单。
用户权限是分层的,这意味着 Read + Write
用户应该拥有与 Read
用户相同的权限以及一些额外的权限。
我现在正在纠结如何创建这个动态菜单。我阅读了 this document on dynamic UIs,我希望我可以纯粹通过使用 conditionalPanel
调用来实现我的目标。
在下面的代码中,您会发现有很多重复项。最糟糕的是,我必须为 tabs
分配唯一的名称,即使它们位于不同的(互斥的)面板(a1
和 a2
)中,但它们的目的恰恰是一样。
到目前为止已经尝试过
我试图将 conditionalPanel
移动到 sidebarMenu
(和 tabItems
分别),但随后出现错误,因为 return 类型 conditionalPanel
与预期类型不匹配。
预期结果
最后,我希望代码重复最少。也就是说,我想为 Do A
和 Do B
定义 一次 ,但是 重新使用 Do A
两个用户。
我有哪些选择?我是否必须回退到动态渲染 (renderUI
/ renderMenu
) 或有什么方法可以仅使用 conditionalPanel
实现所需的行为?
有重复的工作代码
library(shiny)
library(shinydashboard)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(
selectInput("userrights", label = "User Rights:",
choices = c("Read + Write", "Read")),
conditionalPanel("input.userrights == 'Read'",
sidebarMenu(
menuItem("Do A", tabName = "a1")
)
),
conditionalPanel("input.userrights == 'Read + Write'",
sidebarMenu(
## unnecessary duplication + I need yet another tab 'a2'
menuItem("Do A", tabName = "a2"),
menuItem("Do B", tabName = "b2")
)
)
),
dashboardBody(
conditionalPanel("input.userrights == 'Read'",
tabItems(
tabItem("a1", h1("A was done"))
)
),
conditionalPanel("input.userrights == 'Read + Write'",
tabItems(
tabItem("a2", h1("A was done")),
tabItem("b2", h1("B was done"))
)
)
)
)
server <- function(input, output) {}
runApp(shinyApp(ui, server))
片段:不工作但至少 w/o 重复
sidebarMenu(
menuItem("Do A", tabName = "a")
conditionalPanel("input.userrights == 'Read + Write'",
menuItem("Do B", tabName = "b")
)
)
您可以根据用户输入或其他条件在服务器中呈现您的菜单,并将其输出到 UI。下面的工作示例:
library(shiny)
library(shinydashboard)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(
selectInput("userrights", label = "User Rights:",
choices = c("Read + Write", "Read")),
sidebarMenuOutput("menu")
),
dashboardBody(
tabItems(
tabItem("a", h1("A was done")),
tabItem("b", h1("B was done"))
)
)
)
server <- function(input, output) {
output$menu <- renderMenu({
my_list = list(menuItem("a", tabName="a"))
if(input$userrights=="Read + Write")
my_list[[2]] = menuItem("b", tabName="b")
sidebarMenu(my_list)
})
}
runApp(shinyApp(ui, server))
希望对您有所帮助!