diff --git a/core/modules/views/src/Form/ViewsForm.php b/core/modules/views/src/Form/ViewsForm.php
index 2273f90..66348c2 100644
--- a/core/modules/views/src/Form/ViewsForm.php
+++ b/core/modules/views/src/Form/ViewsForm.php
@@ -116,7 +116,7 @@ public function getFormID() {
   /**
    * {@inheritdoc}
    */
-  public function buildForm(array $form, FormStateInterface $form_state, ViewExecutable $view = NULL, $output = NULL) {
+  public function buildForm(array $form, FormStateInterface $form_state, ViewExecutable $view = NULL, $output = []) {
     $form_state['step'] = isset($form_state['step']) ? $form_state['step'] : 'views_form_views_form';
     $form_state['step_controller']['views_form_views_form'] = 'Drupal\views\Form\ViewsFormMainForm';
 
diff --git a/core/modules/views/src/Form/ViewsFormMainForm.php b/core/modules/views/src/Form/ViewsFormMainForm.php
index 6c48b7e..f65310c 100644
--- a/core/modules/views/src/Form/ViewsFormMainForm.php
+++ b/core/modules/views/src/Form/ViewsFormMainForm.php
@@ -22,7 +22,7 @@ public function getFormID() {
   /**
    * {@inheritdoc}
    */
-  public function buildForm(array $form, FormStateInterface $form_state, ViewExecutable $view = NULL, $output = NULL) {
+  public function buildForm(array $form, FormStateInterface $form_state, ViewExecutable $view = NULL, $output = []) {
     $form['#prefix'] = '<div class="views-form">';
     $form['#suffix'] = '</div>';
     $form['#theme'] = 'form';
@@ -30,12 +30,10 @@ public function buildForm(array $form, FormStateInterface $form_state, ViewExecu
 
     // Add the output markup to the form array so that it's included when the form
     // array is passed to the theme function.
-    $form['output'] = array(
-      '#markup' => $output,
-      // This way any additional form elements will go before the view
-      // (below the exposed widgets).
-      '#weight' => 50,
-    );
+    $form['output'] = $output;
+    // This way any additional form elements will go before the view
+    // (below the exposed widgets).
+    $form['output']['#weight'] = 50;
 
     $form['actions'] = array(
       '#type' => 'actions',
diff --git a/core/modules/views/src/Plugin/views/cache/CachePluginBase.php b/core/modules/views/src/Plugin/views/cache/CachePluginBase.php
index 1203a52..5ff74ba 100644
--- a/core/modules/views/src/Plugin/views/cache/CachePluginBase.php
+++ b/core/modules/views/src/Plugin/views/cache/CachePluginBase.php
@@ -142,7 +142,7 @@ public function cacheSet($type) {
         \Drupal::cache($this->resultsBin)->set($this->generateResultsKey(), $data, $this->cacheSetExpire($type), $this->getCacheTags());
         break;
       case 'output':
-        $this->storage['output'] = $this->view->display_handler->output;
+        $this->storage['output'] = drupal_render($this->view->display_handler->output);
         $this->gatherHeaders();
         \Drupal::cache($this->outputBin)->set($this->generateOutputKey(), $this->storage, $this->cacheSetExpire($type), $this->getCacheTags());
         break;
diff --git a/core/modules/views/src/Plugin/views/display/DisplayPluginBase.php b/core/modules/views/src/Plugin/views/display/DisplayPluginBase.php
index b224567..13fef4f 100644
--- a/core/modules/views/src/Plugin/views/display/DisplayPluginBase.php
+++ b/core/modules/views/src/Plugin/views/display/DisplayPluginBase.php
@@ -13,6 +13,7 @@
 use Drupal\Core\Language\LanguageInterface;
 use Drupal\Core\Session\AccountInterface;
 use Drupal\Core\Theme\Registry;
+use Drupal\views\Form\ViewsForm;
 use Drupal\views\Plugin\views\area\AreaPluginBase;
 use Drupal\views\ViewExecutable;
 use Drupal\views\Plugin\views\PluginBase;
@@ -2135,11 +2136,82 @@ public function getMenuLinks() {
    * Render this display.
    */
   public function render() {
+    $rows = (!empty($this->view->result) || $this->view->style_plugin->evenEmpty()) ? $this->view->style_plugin->render($this->view->result) : array();
+
     $element = array(
       '#theme' => $this->themeFunctions(),
       '#view' => $this->view,
+      '#attached' => &$this->view->element['#attached'],
+      '#pre_render' => [[$this, 'elementPreRender']],
+      '#rows' => $rows,
     );
-    $element['#attached'] = &$this->view->element['#attached'];
+
+    return $element;
+  }
+
+  /**
+   * Pre render callback for view display rendering.
+   *
+   * @see self::render()
+   *
+   * @param array $element
+   *
+   * @return array
+   */
+  public function elementPreRender($element) {
+    $view = $element['#view'];
+    $empty = empty($view->result);
+
+    // Force a render array so CSS/JS can be added.
+    if (!is_array($element['#rows'])) {
+      $element['#rows'] = array('#markup' => $element['#rows']);
+    }
+
+    $element['#header'] = $view->display_handler->renderArea('header', $empty);
+    $element['#footer'] = $view->display_handler->renderArea('footer', $empty);
+    $element['#empty'] = $empty ? $view->display_handler->renderArea('empty', $empty) : array();
+    $element['#exposed'] = !empty($view->exposed_widgets) ? $view->exposed_widgets : array();
+    $element['#more'] = $view->display_handler->renderMoreLink();
+    $element['#feed_icon'] = !empty($view->feed_icon) ? $view->feed_icon : array();
+
+    if ($view->display_handler->renderPager()) {
+      $exposed_input = isset($view->exposed_raw_input) ? $view->exposed_raw_input : NULL;
+      $element['#pager'] = $view->renderPager($exposed_input);
+    }
+
+    if (!empty($view->attachment_before)) {
+      $element['#attachment_before'] = $view->attachment_before;
+    }
+    if (!empty($view->attachment_after)) {
+      $element['#attachment_after'] = $view->attachment_after;
+    }
+
+    // If form fields were found in the view, reformat the view output as a form.
+    if ($view->hasFormElements()) {
+      // Only render row output if there are rows. Otherwise, render the empty
+      // region.
+      if (!empty($element['#rows'])) {
+        $output = $element['#rows'];
+      }
+      else {
+        $output = $element['#empty'];
+      }
+
+      $form_object = ViewsForm::create(\Drupal::getContainer(), $view->storage->id(), $view->current_display);
+      $form = \Drupal::formBuilder()->getForm($form_object, $view, $output);
+      // The form is requesting that all non-essential views elements be hidden,
+      // usually because the rendered step is not a view result.
+      if ($form['show_view_elements']['#value'] == FALSE) {
+        $element['#header'] = array();
+        $element['#exposed'] = array();
+        $element['#pager'] = array();
+        $element['#footer'] = array();
+        $element['#more'] = array();
+        $element['#feed_icon'] = array();
+      }
+
+      $element['#rows'] = $form;
+    }
 
     return $element;
   }
diff --git a/core/modules/views/src/Plugin/views/display/Feed.php b/core/modules/views/src/Plugin/views/display/Feed.php
index a6e6fdd..c621578 100644
--- a/core/modules/views/src/Plugin/views/display/Feed.php
+++ b/core/modules/views/src/Plugin/views/display/Feed.php
@@ -80,7 +80,7 @@ public function execute() {
 
     $response = $this->view->getResponse();
 
-    $response->setContent($output);
+    $response->setContent(drupal_render($output));
 
     return $response;
   }
diff --git a/core/modules/views/src/Plugin/views/style/Rss.php b/core/modules/views/src/Plugin/views/style/Rss.php
index 996684d..0492bbd 100644
--- a/core/modules/views/src/Plugin/views/style/Rss.php
+++ b/core/modules/views/src/Plugin/views/style/Rss.php
@@ -44,14 +44,10 @@ public function attachTo($display_id, $path, $title) {
     $url = url($this->view->getUrl(NULL, $path), $url_options);
     if ($display->hasPath()) {
       if (empty($this->preview)) {
-        $build['#attached']['drupal_add_feed'][] = array($url, $title);
-        drupal_render($build);
+        drupal_add_feed($url, $title);
       }
     }
     else {
-      if (empty($this->view->feed_icon)) {
-        $this->view->feed_icon = '';
-      }
       $feed_icon = array(
         '#theme' => 'feed_icon',
         '#url' => $url,
@@ -63,7 +59,7 @@ public function attachTo($display_id, $path, $title) {
         'title' => $title,
         'href' => $url,
       );
-      $this->view->feed_icon .= drupal_render($feed_icon);
+      $this->view->feed_icon = $feed_icon;
     }
   }
 
@@ -115,7 +111,7 @@ public function getDescription() {
   public function render() {
     if (empty($this->view->rowPlugin)) {
       debug('Drupal\views\Plugin\views\style\Rss: Missing row plugin');
-      return;
+      return array();
     }
     $rows = '';
 
@@ -144,7 +140,7 @@ public function render() {
       '#rows' => SafeMarkup::set($rows),
     );
     unset($this->view->row_index);
-    return drupal_render($build);
+    return $build;
   }
 
 }
diff --git a/core/modules/views/src/Plugin/views/style/StylePluginBase.php b/core/modules/views/src/Plugin/views/style/StylePluginBase.php
index 6bb8cb1..9b26e4f 100644
--- a/core/modules/views/src/Plugin/views/style/StylePluginBase.php
+++ b/core/modules/views/src/Plugin/views/style/StylePluginBase.php
@@ -475,9 +475,7 @@ public function renderGroupingSets($sets, $level = 0) {
         if ($this->usesRowPlugin()) {
           foreach ($set['rows'] as $index => $row) {
             $this->view->row_index = $index;
-            $render = $this->view->rowPlugin->render($row);
-            // Row render arrays cannot be contained by style render arrays.
-            $set['rows'][$index] = drupal_render($render);
+            $set['rows'][$index] = $this->view->rowPlugin->render($row);
           }
         }
 
diff --git a/core/modules/views/views.module b/core/modules/views/views.module
index 3294836..31c6a7f 100644
--- a/core/modules/views/views.module
+++ b/core/modules/views/views.module
@@ -129,7 +129,21 @@ function views_theme($existing, $type, $theme, $path) {
     // For displays, we pass in a dummy array as the first parameter, since
     // $view is an object but the core contextual_preprocess() function only
     // attaches contextual links when the primary theme argument is an array.
-    'display' => array('view_array' => array(), 'view' => NULL),
+    'display' => array(
+      'view_array' => array(),
+      'view' => NULL,
+      'rows' => array(),
+      'header' => array(),
+      'footer' => array(),
+      'empty' => array(),
+      'exposed' => array(),
+      'more' => array(),
+      'feed_icon' => array(),
+      'pager' => array(),
+      'title' => '',
+      'attachment_before' => array(),
+      'attachment_after' => array(),
+    ),
     'style' => array('view' => NULL, 'options' => NULL, 'rows' => NULL, 'title' => NULL),
     'row' => array('view' => NULL, 'options' => NULL, 'row' => NULL, 'field_alias' => NULL),
     'exposed_form' => array('view' => NULL, 'options' => NULL),
@@ -818,11 +832,12 @@ function views_pre_render_views_form_views_form($element) {
   }
 
   // Apply substitutions to the rendered output.
-  $element['output']['#markup'] = str_replace($search, $replace, $element['output']['#markup']);
+  $element['output'] = array('#markup' => str_replace($search, $replace, drupal_render($element['output'])));
 
   // Sort, render and add remaining form fields.
   $children = Element::children($element, TRUE);
   $element['#children'] = drupal_render_children($element, $children);
+
   return $element;
 }
 
diff --git a/core/modules/views/views.theme.inc b/core/modules/views/views.theme.inc
index 5a06397..a0b6b72 100644
--- a/core/modules/views/views.theme.inc
+++ b/core/modules/views/views.theme.inc
@@ -23,20 +23,13 @@
  */
 function template_preprocess_views_view(&$variables) {
   $view = $variables['view'];
+  $id = $view->storage->id();
 
-  $variables['rows'] = (!empty($view->result) || $view->style_plugin->evenEmpty()) ? $view->style_plugin->render($view->result) : array();
-  // Force a render array so CSS/JS can be added.
-  if (!is_array($variables['rows'])) {
-    $variables['rows'] = array('#markup' => $variables['rows']);
-  }
-
-  $variables['css_name'] = drupal_clean_css_identifier($view->storage->id());
-  $variables['id'] = $view->storage->id();
+  $variables['css_name'] = drupal_clean_css_identifier($id);
+  $variables['id'] = $id;
   $variables['display_id'] = $view->current_display;
 
   // Basic classes.
-  $variables['css_class'] = '';
-
   $variables['attributes']['class'] = array();
   $variables['attributes']['class'][] = 'view';
   $variables['attributes']['class'][] = 'view-' . drupal_clean_css_identifier($variables['id']);
@@ -49,39 +42,6 @@ function template_preprocess_views_view(&$variables) {
     $variables['attributes']['class'][] = $variables['css_class'];
   }
 
-  $empty = empty($view->result);
-  $variables['header'] = $view->display_handler->renderArea('header', $empty);
-  $variables['footer'] = $view->display_handler->renderArea('footer', $empty);
-  $variables['empty'] = $empty ? $view->display_handler->renderArea('empty', $empty) : FALSE;
-
-  $variables['exposed']    = !empty($view->exposed_widgets) ? $view->exposed_widgets : '';
-  $variables['more']       = $view->display_handler->renderMoreLink();
-  $variables['feed_icon']  = !empty($view->feed_icon) ? $view->feed_icon : '';
-
-  $variables['pager']      = '';
-
-  // @todo: Figure out whether this belongs into views_ui_preprocess_views_view.
-  // Render title for the admin preview.
-  $variables['title'] = !empty($view->views_ui_context) ? Xss::filterAdmin($view->getTitle()) : '';
-
-  if ($view->display_handler->renderPager()) {
-    $exposed_input = isset($view->exposed_raw_input) ? $view->exposed_raw_input : NULL;
-    $variables['pager'] = $view->renderPager($exposed_input);
-  }
-
-  if (!empty($view->attachment_before)) {
-    $variables['attachment_before'] = $view->attachment_before;
-  }
-  else {
-    $variables['attachment_before'] = array();
-  }
-  if (!empty($view->attachment_after)) {
-    $variables['attachment_after'] = $view->attachment_after;
-  }
-  else {
-    $variables['attachment_after'] = array();
-  }
-
   // Add contextual links to the view. We need to attach them to the dummy
   // $view_array variable, since contextual_preprocess() requires that they be
   // attached to an array (not an object) in order to process them. For our
@@ -105,36 +65,6 @@ function template_preprocess_views_view(&$variables) {
     $variables['dom_id'] = $view->dom_id;
     $variables['attributes']['class'][] = 'view-dom-id-' . $variables['dom_id'];
   }
-
-  // If form fields were found in the view, reformat the view output as a form.
-  if ($view->hasFormElements()) {
-    // Copy the rows so as not to modify them by reference when rendering.
-    $rows = $variables['rows'];
-    // Only render row output if there are rows. Otherwise, render the empty
-    // region.
-    if (!empty($rows)) {
-      $output = drupal_render($rows);
-    }
-    else {
-      $empty = $variables['empty'];
-      $output = drupal_render($empty);
-    }
-
-    $container = \Drupal::getContainer();
-    $form_object = new ViewsForm($container->get('class_resolver'), $container->get('url_generator'), $container->get('request_stack'), $view->storage->id(), $view->current_display);
-    $form = \Drupal::formBuilder()->getForm($form_object, $view, $output);
-    // The form is requesting that all non-essential views elements be hidden,
-    // usually because the rendered step is not a view result.
-    if ($form['show_view_elements']['#value'] == FALSE) {
-      $variables['header'] = '';
-      $variables['exposed'] = '';
-      $variables['pager'] = '';
-      $variables['footer'] = '';
-      $variables['more'] = '';
-      $variables['feed_icon'] = '';
-    }
-    $variables['rows'] = $form;
-  }
 }
 
 /**
diff --git a/core/modules/views_ui/src/ViewUI.php b/core/modules/views_ui/src/ViewUI.php
index 9ac7d46..dff1104 100644
--- a/core/modules/views_ui/src/ViewUI.php
+++ b/core/modules/views_ui/src/ViewUI.php
@@ -589,7 +589,6 @@ public function renderPreview($display_id, $args = array()) {
     if (empty($errors)) {
       $this->ajax = TRUE;
       $this->executable->live_preview = TRUE;
-      $this->views_ui_context = TRUE;
 
       // AJAX happens via HTTP POST but everything expects exposed data to
       // be in GET. Copy stuff but remove ajax-framework specific keys.
diff --git a/core/modules/views_ui/views_ui.module b/core/modules/views_ui/views_ui.module
index f27d515..ba63358 100644
--- a/core/modules/views_ui/views_ui.module
+++ b/core/modules/views_ui/views_ui.module
@@ -13,6 +13,7 @@
 use Drupal\views\Analyzer;
 use Drupal\Core\Ajax\AjaxResponse;
 use Drupal\Core\Ajax\ReplaceCommand;
+use Drupal\Component\Utility\Xss;
 
 /**
  * Implements hook_help().
@@ -141,6 +142,12 @@ function views_ui_permission() {
  */
 function views_ui_preprocess_views_view(&$variables) {
   $view = $variables['view'];
+
+  // Render title for the admin preview.
+  if (!empty($view->live_preview)) {
+    $variables['title'] = Xss::filterAdmin($view->getTitle());
+  }
+
   if (!empty($view->live_preview) && \Drupal::moduleHandler()->moduleExists('contextual')) {
     $view->setShowAdminLinks(FALSE);
     foreach (array('title', 'header', 'exposed', 'rows', 'pager', 'more', 'footer', 'empty', 'attachment_after', 'attachment_before') as $section) {
