diff --git a/config/install/dfp.settings.yml b/config/install/dfp.settings.yml
index c5da9ab..63c8857 100644
--- a/config/install/dfp.settings.yml
+++ b/config/install/dfp.settings.yml
@@ -4,6 +4,11 @@ click_url: ''
 async_rendering: true
 disable_init_load: false
 single_request: true
+lazy_load:
+  enabled: false
+  fetch_margin: 500
+  render_margin: 200
+  mobile_scaling: 2.0
 default_slug: ''
 collapse_empty_divs: 1
 hide_slug: true
diff --git a/config/schema/dfp.schema.yml b/config/schema/dfp.schema.yml
index 78c105f..38575bc 100644
--- a/config/schema/dfp.schema.yml
+++ b/config/schema/dfp.schema.yml
@@ -22,6 +22,22 @@ dfp.settings:
     single_request:
       type: boolean
       label: 'Use a single request'
+    lazy_load:
+      type: mapping
+      label: 'Lazyload Settings'
+      mapping:
+        enabled:
+          type: boolean
+          label: 'Enable lazy loading'
+        fetch_margin:
+          type: integer
+          label: 'Fetch Margin Percent'
+        render_margin:
+          type: integer
+          label: 'Render Margin Percent'
+        mobile_scaling:
+          type: float
+          label: 'Mobile Scaling'
     default_slug:
       type: string
       label: 'The default slug'
diff --git a/dfp.install b/dfp.install
new file mode 100644
index 0000000..8de8e57
--- /dev/null
+++ b/dfp.install
@@ -0,0 +1,25 @@
+<?php
+
+/**
+ * @file
+ * Update hooks for DFP module.
+ */
+
+/**
+ * Set default values for global lazy loading.
+ */
+function dfp_update_8001() {
+  $config_factory = \Drupal::configFactory();
+  $config = $config_factory->getEditable('dfp.settings');
+  $config->set('lazy_load', [
+    'enabled' => FALSE,
+    'fetch_margin' => 500,
+    'render_margin' => 200,
+    'mobile_scaling' => 2.0,
+  ]);
+  $config->save(TRUE);
+
+  // Force UI to use the new config value by invalidating entry from
+  // cache.config bin.
+  \Drupal::service('cache.config')->invalidate('dfp.settings');
+}
diff --git a/dfp.module b/dfp.module
index f00a0a9..02a052d 100755
--- a/dfp.module
+++ b/dfp.module
@@ -45,6 +45,7 @@ function dfp_theme() {
       'variables' => [
         'async_rendering' => NULL,
         'single_request' => NULL,
+        'lazy_load' => NULL,
         'collapse_empty_divs' => NULL,
         'disable_init_load' => NULL,
         'targeting' => [],
diff --git a/src/DfpHtmlResponseAttachmentsProcessor.php b/src/DfpHtmlResponseAttachmentsProcessor.php
index e475f61..e6befcd 100644
--- a/src/DfpHtmlResponseAttachmentsProcessor.php
+++ b/src/DfpHtmlResponseAttachmentsProcessor.php
@@ -168,6 +168,7 @@ class DfpHtmlResponseAttachmentsProcessor extends HtmlResponseAttachmentsProcess
       '#theme' => 'dfp_js_head_bottom',
       '#async_rendering' => $global_settings->get('async_rendering'),
       '#single_request' => $global_settings->get('single_request'),
+      '#lazy_load' => $global_settings->get('lazy_load'),
       '#collapse_empty_divs' => $global_settings->get('collapse_empty_divs'),
       '#disable_init_load' => $global_settings->get('disable_init_load'),
       '#targeting' => $targeting,
diff --git a/src/Form/AdminSettings.php b/src/Form/AdminSettings.php
index 5f1a243..11ff1f1 100644
--- a/src/Form/AdminSettings.php
+++ b/src/Form/AdminSettings.php
@@ -131,6 +131,52 @@ class AdminSettings extends ConfigFormBase {
       '#description' => $this->t('This can speed up page rendering time by limiting the number of external requests.'),
     ];
 
+    $form['global_tag_settings']['lazy_load_enabled'] = [
+      '#type' => 'checkbox',
+      '#title' => $this->t('Enable lazy loading'),
+      '#description' => $this->t('Enable lazy-loading for all the ad slots.'),
+      '#default_value' => $config->get('lazy_load')['enabled'] ?? FALSE,
+    ];
+
+    $form['global_tag_settings']['lazy_load_fetch_margin'] = [
+      '#type' => 'number',
+      '#title' => $this->t('Fetch Margin Percent'),
+      '#default_value' => $config->get('lazy_load')['fetch_margin'] ?? 500,
+      '#description' => t('Minimum distance from the current viewport a slot must be before we fetch the ad as a percentage of viewport size. 0 means "when the slot enters the viewport", 100 means "when the ad is 1 viewport away", and so on.'),
+      '#states' => [
+        'visible' => [
+          'input[name="lazy_load_enabled"]' => ['checked' => TRUE],
+        ],
+      ],
+    ];
+
+    $form['global_tag_settings']['lazy_load_render_margin'] = [
+      '#type' => 'number',
+      '#title' => $this->t('Render Margin Percent'),
+      '#default_value' => $config->get('lazy_load')['render_margin'] ?? 200,
+      '#description' => t('Minimum distance from the current viewport a slot must be before we render an ad. This allows for prefetching the ad, but waiting to render and download other subresources. The value works just like Fetch Margin Percent as a percentage of viewport.'),
+      '#states' => [
+        'visible' => [
+          'input[name="lazy_load_enabled"]' => ['checked' => TRUE],
+        ],
+      ],
+    ];
+
+    $form['global_tag_settings']['lazy_load_mobile_scaling'] = [
+      '#type' => 'number',
+      '#title' => $this->t('Mobile Scaling'),
+      '#default_value' => $config->get('lazy_load')['mobile_scaling'] ?? 2.0,
+      '#min' => 1.0,
+      '#max' => 10.0,
+      '#step' => 0.5,
+      '#description' => t('Multiplier applied to margins on mobile devices. This allows varying margins on mobile vs. desktop. For example, a value of 2.0 will multiply all margins by 2 on mobile devices, increasing the minimum distance a slot can be before fetching and rendering.'),
+      '#states' => [
+        'visible' => [
+          'input[name="lazy_load_enabled"]' => ['checked' => TRUE],
+        ],
+      ],
+    ];
+
     // Global display options.
     $form['global_display_options'] = [
       '#type' => 'details',
@@ -221,6 +267,12 @@ class AdminSettings extends ConfigFormBase {
       ->set('async_rendering', $values['async_rendering'])
       ->set('disable_init_load', $values['disable_init_load'])
       ->set('single_request', $values['single_request'])
+      ->set('lazy_load', [
+        'enabled' => $values['lazy_load_enabled'],
+        'fetch_margin' => $values['lazy_load_fetch_margin'],
+        'render_margin' => $values['lazy_load_render_margin'],
+        'mobile_scaling' => $values['lazy_load_mobile_scaling'],
+      ])
       ->set('default_slug', $values['default_slug'])
       ->set('collapse_empty_divs', $values['collapse_empty_divs'])
       ->set('adtest_adunit_pattern', $values['adtest_adunit_pattern'])
diff --git a/templates/dfp-js-head-bottom.html.twig b/templates/dfp-js-head-bottom.html.twig
index c90cd76..2211259 100644
--- a/templates/dfp-js-head-bottom.html.twig
+++ b/templates/dfp-js-head-bottom.html.twig
@@ -6,6 +6,7 @@
  * Available variables:
  * - async_rendering
  * - single_request
+ * - lazy_load
  * - collapse_empty_divs
  * - disable_init_load
  * - targeting
@@ -40,6 +41,15 @@ googletag.cmd.push(function() {
       {%- endfor -%}
     ]);
   {% endfor %}
+
+  {% if lazy_load.enabled %}
+    googletag.pubads().enableLazyLoad({
+      fetchMarginPercent: {{ lazy_load.fetch_margin }},
+      renderMarginPercent: {{ lazy_load.render_margin }},
+      mobileScaling: {{ lazy_load.mobile_scaling }}
+    });
+  {% endif %}
+
+  googletag.enableServices();
 });
-googletag.enableServices();
 </script>
