def _create_subplots(self, layout, positions, layout_dimensions, ranges, axes={}, num=1, create=True):
        """
        Plot all the views contained in the AdjointLayout Object using axes
        appropriate to the layout configuration. All the axes are
        supplied by LayoutPlot - the purpose of the call is to
        invoke subplots with correct options and styles and hide any
        empty axes as necessary.
        """
        subplots = {}
        projections = []
        adjoint_clone = layout.clone(shared_data=False, id=layout.id)
        subplot_opts = dict(show_title=False, adjoined=layout)
        for pos in positions:
            # Pos will be one of 'main', 'top' or 'right' or None
            view = layout.get(pos, None)
            if not displayable(view):
                view = collate(view)
            ax = axes.get(pos, None)
            if view is None or not view.traverse(lambda x: x, [Element]):
                projections.append(None)
                continue

            # Determine projection type for plot
            projections.append(self._get_projection(view))

            if not create:
                continue

            # Customize plotopts depending on position.
            plotopts = self.lookup_options(view, 'plot').options

            # Options common for any subplot
            override_opts = {}
            sublabel_opts = {}
            if pos == 'main':
                own_params = self.get_param_values(onlychanged=True)
                sublabel_opts = {k: v for k, v in own_params
                                 if 'sublabel_' in k}
            elif pos == 'right':
                right_opts = dict(invert_axes=True,
                                  xaxis=None)
                override_opts = dict(subplot_opts, **right_opts)
            elif pos == 'top':
                top_opts = dict(yaxis=None)
                override_opts = dict(subplot_opts, **top_opts)

            # Override the plotopts as required
            plotopts = dict(sublabel_opts, **plotopts)
            plotopts.update(override_opts, fig=self.handles['fig'])
            vtype = view.type if isinstance(view, HoloMap) else view.__class__
            if isinstance(view, GridSpace):
                plotopts['create_axes'] = ax is not None
            plot_type = Store.registry['matplotlib'][vtype]
            if pos != 'main' and vtype in MPLPlot.sideplots:
                plot_type = MPLPlot.sideplots[vtype]
            num = num if len(self.coords) > 1 else 0
            subplots[pos] = plot_type(view, axis=ax, keys=self.keys,
                                      dimensions=self.dimensions,
                                      layout_dimensions=layout_dimensions,
                                      ranges=ranges, subplot=True,
                                      uniform=self.uniform, layout_num=num,
                                      renderer=self.renderer, **plotopts)
            if isinstance(view, (Element, HoloMap, Collator, CompositeOverlay)):
                adjoint_clone[pos] = subplots[pos].hmap
            else:
                adjoint_clone[pos] = subplots[pos].layout
        return subplots, adjoint_clone, projections
Plot all the views contained in the AdjointLayout Object using axes
        appropriate to the layout configuration. All the axes are
        supplied by LayoutPlot - the purpose of the call is to
        invoke subplots with correct options and styles and hide any
        empty axes as necessary.