% Generated by roxygen2: do not edit by hand
% Please edit documentation in R/paintr-plotly.R
\name{ptr_plotly_selection}
\alias{ptr_plotly_selection}
\title{Read a \code{ptr_ggplotly()} Linked Selection As Rows or a Flag Column}
\usage{
ptr_plotly_selection(state, mode = c("rows", "flag"), source = NULL)
}
\arguments{
\item{state}{A \code{ptr_state} handle as returned by \code{\link[=ptr_server]{ptr_server()}}.}

\item{mode}{\code{"rows"} (default) or \code{"flag"} — which projection of the one
selection to return. Any other value aborts (the bare-indices projection
is rejected by design).}

\item{source}{Character scalar for plotly's \verb{source =} channel, or \code{NULL}
(default) to derive the same distinct string \code{\link[=ptr_ggplotly]{ptr_ggplotly()}} derives from
the instance namespace.}
}
\value{
A Shiny reactive. Its value is the rows projection (a data frame, the
selected slice; zero rows, same columns, when empty) or the flag projection
(the full drawn data plus a logical \code{.ptr_selected}), per \code{mode}.
}
\description{
\code{ptr_plotly_selection()} is the companion reader for \code{\link[=ptr_ggplotly]{ptr_ggplotly()}}: it
returns a Shiny reactive carrying the current brush/lasso selection of the
plotly widget, projected one of two ways. Call it once in your server (not
inside a render) on the live instance returned by \code{\link[=ptr_server]{ptr_server()}} and feed
the returned reactive to a table, a second formula, or any downstream
consumer.
}
\details{
A selection names rows of the \strong{drawn data} — \code{state$runtime()$plot$data}
of the draw that produced the widget — never "the original object". Keys are
minted per draw and are meaningless across draws, so the selection
\strong{resets to empty on every draw} (a redraw after a \code{filter()}/\code{mutate()}
pipeline-head change or an upload swap starts the selection over). A
\code{plotly_deselect} event clears it likewise. Two projections of the one
selection:
\itemize{
\item \code{mode = "rows"} — the selected slice; a \strong{zero-row data frame with the
drawn data's columns} when nothing is selected (so a \code{\link[shiny:renderTable]{shiny::renderTable()}}
consumer needs no \code{req()} dance).
\item \code{mode = "flag"} — the \strong{full} drawn data plus a logical \code{.ptr_selected}
column, \code{TRUE} exactly at the selected rows (all \code{FALSE} when empty).
}

\code{.ptr_selected} is a reserved name: a pre-existing \code{.ptr_selected} on the
drawn data is silently overwritten (the overwrite keeps chained
selection-fed instances correct). The internal \code{.ptr_row} key never appears
in either projection.

\strong{Pre-draw window:} before the first draw there is no snapshot yet, so the
returned reactive raises Shiny's silent pre-draw condition (via
\code{\link[shiny:req]{shiny::req()}}); under live mode a selection-fed instance shows its inline
pre-draw state for one flush. \strong{Live-mode key reset:} changing a placeholder
widget re-draws the source plot, which re-mints the keys, so the selection
resets to empty on that picker change.

plotly is an optional dependency (in \code{Suggests}); this reader is only
meaningful alongside \code{\link[=ptr_ggplotly]{ptr_ggplotly()}}, which guards on plotly being
installed.
}
\examples{
if (interactive()) {
library(shiny)
library(plotly)
f <- rlang::expr(
  ggplot(mtcars, aes(x = ppVar(wt), y = ppVar(mpg))) + geom_point()
)
ui <- ptr_ui_page(
  ptr_ui_controls(formula = f, id = "p"),
  plotly::plotlyOutput("plt"),
  tableOutput("sel")
)
server <- function(input, output, session) {
  state <- ptr_server(f, "p")
  output$plt <- plotly::renderPlotly({
    ptr_ggplotly(state, tooltip = "all")
  })
  # Full loop: brush the plot -> the selected rows appear in the table.
  sel <- ptr_plotly_selection(state, mode = "rows")
  output$sel <- renderTable(sel())
}
shinyApp(ui, server)
}

}
\seealso{
\code{\link[=ptr_ggplotly]{ptr_ggplotly()}} for the widget side; \code{\link[=ptr_server]{ptr_server()}} for the L3
custom-render contract.
}
