How to get AMP Cookie consent modal dialog backdrop working?

1k views Asked by At

I'd like to implement a cookie consent on my static AMP website. The amp-story-consent so far seems to not fit that (cookie consent has no pages or bookend, please chip in if you know a solution for How to construct AMP cookie consent with the help of amp-story-consent?). I'm trying to implement my own modal dialog following the examples.

<amp-consent layout="nodisplay" id="cookie-consent-element">
  <script type="application/json">
  {
    "consents": {
      "my-consent": {
        "checkConsentHref": "https://amp.dev/documentation/examples/api/get-consent",
        "promptUI": "cookie-consent-ui"
      }
    }
  }
  </script>
  <div id="cookie-consent-ui" class="card col-lg-6 col-md-8 col-sm-10 col-xs-12" aria-labelledby="cookie-consent-title" role="dialog">
    <h2 id="cookie-consent-title">Cookie Consent</h2>
    <p>
      Lorem ipsum dolor sit amet, list of cookies
    </p>
    <ul>
      <li>
         ...
      </li>
    </ul>
    <button type="button" on="tap:cookie-consent-element.accept" class="btn--primary" role="button">Accept</button>
    <button type="button" on="tap:cookie-consent-element.reject" class="btn--secondary" role="button">Reject</button>
  </div>
  <div id="modal-overlay" tabindex="-1">
  </div>
</amp-consent>

Related styles:

#modal-overlay {
    width: 100%;
    height: 100%;
    z-index: 1002; /* places the modal overlay between the main page and the modal dialog*/
    background-color: #000;
    opacity: 0.5;
    position: fixed;
    top: 0;
    left: 0;
    margin: 0;
    padding: 0;
}

#cookie-consent-ui {
    margin-left: auto;
    margin-right: auto;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    z-index: 1003; /* places the modal dialog on top of everything else */
    position: fixed;
}
#cookie-consent-ui h2 {
    text-align: center;
}

I'm at the phase when the dialog is shown. Problems I have: 1. The modal-overlay gets a hidden attribute (I guess from some AMP logic) so it does not cover the surroundings of the modal dialog as a backdrop. 2. If I manually show it (deleting the hidden in the debugger) I can still tab out the focus off of the dialog to the background elements. The tabindex=-1 supposed to prevent that, not working.

So how can I make the backdrop show with the dialog? Otherwise this seems to work once the user accepts or rejects the consent: I added data-block-on-consent to the related amp elements, and the dialog doesn't show any more. Should I maybe experiment with the combination of amp-user-notification and amp-consent?

1

There are 1 answers

1
Csaba Toth On BEST ANSWER

I ended up using amp-lightbox to cast a backdrop for the modal dialog. I wish this would have been mentioned right away in some examples. I embedded the modal dialog and the backdrop tag into an amp-lightbox this way:

<amp-consent layout="nodisplay" id="cookie-consent-element">
  <script type="application/json">
  {
    "consentInstanceId": "cookie-consent",
    "consentRequired": true,
    "promptUI": "cookie-consent-ui-lightbox"
  }
  </script>
  <amp-lightbox id="cookie-consent-ui-lightbox" layout="nodisplay" tabindex="-1">
   <div id="cookie-consent-ui" class="card col-lg-6 col-md-8 col-sm-10 col-11" aria-labelledby="cookie-consent-title" role="dialog">
    <h2 id="cookie-consent-title">Cookie Consent</h2>
    <p>
      Lorem ipsum dolor sit amet, list of cookies
    </p>
    <ul>
      <li>
         ...
      </li>
    </ul>
    <button type="button" on="tap:cookie-consent-element.accept" class="btn--primary" role="button">Accept</button>
    <button type="button" on="tap:cookie-consent-element.reject" class="btn--secondary" role="button">Reject</button>
   </div>
   <div id="cookie-consent-backdrop" tabindex="-1">
   </div>
  </amp-lightbox>
</amp-consent>

When I embed the dialog and the backdrop into the lightbox, the backdrop doesn't get hidden and the tabindex="-1" seems to work as well. One improvement compared to the question is that I don't use any dummy REST endpoint "checkConsentHref": "https://amp.dev/documentation/examples/api/get-consent", but I just simply use "consentRequired": true. Unfortunately including the lightbox

<script async custom-element="amp-lightbox" src="https://cdn.ampproject.org/v0/amp-lightbox-0.1.js"></script>

means an extra 7.3 KB (amp-lightbox-0.1.js) + 2.7 KB (amp-auto-lightbox-0.1.js) = 10 KB of JavaScript needs to be downloaded, but that's still much better than the amp-story-consent route where amp-story-0.1.js would be 81.4 KB, which is even more than the AMP's mother v0.js 71.7 KB.


I also opened an issue at the AMP project about this asking for an official example: https://github.com/ampproject/amp.dev/issues/3988

Here is my own website for reference: https://gitlab.com/MrCsabaToth/mrcsabatoth.gitlab.io/-/blob/master/_layouts/default.html#L56