class_docstr: A grid of :class:`PlotlyViewPlot` instances.
  
  Args:
      plots: a :class:`PlotlyViewPlot` or iterable of :class:`PlotlyViewPlot`
          instances
      shape (None): the ``(rows, cols)`` shape to use for the grid
      hgap (None): a horizontal spacing between the subplots, in ``[0, 1]``
      vgap (None): a vertical spacing between the subplots, in ``[0, 1]``
      init_view (None): an optional initial
          :class:`fiftyone.core.collections.SampleCollection` to load
      **kwargs: optional parameters for
          :meth:`plotly:plotly.graph_objects.Figure.update_layout`
code: def __init__(
      self,
      plots,
      shape=None,
      hgap=None,
      vgap=None,
      init_view=None,
      **kwargs,
  ):
      if not etau.is_container(plots):
          plots = [plots]
  
      bad_plots = [
          p for p in plots if not isinstance(p, PlotlyViewPlot)
      ]
      if bad_plots:
          raise ValueError(
              "Found %d unsupported plots; this class only supports %s plots"
              % (len(bad_plots), PlotlyViewPlot)
          )
  
      self.plots = plots
      self.shape = shape
      self.hgap = hgap
      self.vgap = vgap
      self.layout = kwargs
  
      self._aggregations = None
      self._agg_lengths = None
  
      self._init_aggregations()
  
      widget = self._make_widget()
  
      super().__init__(widget, init_view=init_view)
  
imports: import itertools
  from operator import itemgetter
  import numpy
  import eta.core.utils
  import plotly.subplots
  import plotly.graph_objects
  import fiftyone.core.aggregations
  from .base import ViewPlot
  from .plotly import PlotlyWidgetMixin
label_desc: Use image node_id 1 to create a new ViewGrid object from inherited base classes: PlotlyViewPlot with example: obj = ViewGrid(plots, shape, hgap, vgap, init_view)