@expofp/floorplan
Version:
Interactive floor plan library for expos and events
2 lines (1 loc) • 2.97 kB
JavaScript
import{jsx as a,jsxs as h}from"react/jsx-runtime";import"./Modal.scss";import O from"classnames";import{useEffect as b,useId as S,useRef as I,useState as k}from"react";import{createPortal as j}from"react-dom";import B from"../Button";const C=200,M=n=>n.getClientRects().length>0&&getComputedStyle(n).visibility!=="hidden",P=({open:n,className:w,variant:E="default",title:s,ariaLabel:q,maxWidth:_,children:D,closeLabel:y,renderTarget:A,footerLeft:u=[],footerRight:f=[],onClose:c})=>{const p=I(null),d=I(null),F=S(),[v,N]=k(n),[T,g]=k(n);if(b(()=>{if(!n){const i=requestAnimationFrame(()=>N(!1)),l=setTimeout(()=>g(!1),C);return d.current?.focus(),d.current=null,()=>{cancelAnimationFrame(i),clearTimeout(l)}}d.current||(d.current=document.activeElement);const t=document.body.style.overflow;document.body.style.overflow="hidden";let e=0;const r=requestAnimationFrame(()=>{g(!0),e=requestAnimationFrame(()=>N(!0))});return()=>{cancelAnimationFrame(r),cancelAnimationFrame(e),document.body.style.overflow=t}},[n]),b(()=>{if(!n)return;const t=e=>{if(e.key==="Escape"){e.preventDefault(),e.stopImmediatePropagation(),c();return}if(e.key!=="Tab")return;const r=p.current;if(!r)return;const i=Array.from(r.querySelectorAll('a[href], button:not([disabled]), input:not([disabled]), select:not([disabled]), textarea:not([disabled]), [tabindex]:not([tabindex="-1"])')).filter(M);if(i.length===0){e.preventDefault();return}const l=i[0],m=i[i.length-1],o=document.activeElement;e.shiftKey?(o===l||o===r)&&(e.preventDefault(),m.focus()):o===m&&(e.preventDefault(),l.focus())};return document.addEventListener("keydown",t),()=>document.removeEventListener("keydown",t)},[n,c]),b(()=>{if(!v)return;let t=0;const e=requestAnimationFrame(()=>{t=requestAnimationFrame(()=>p.current?.focus())});return()=>{cancelAnimationFrame(e),cancelAnimationFrame(t)}},[v]),!T||!A)return null;const x=t=>t?.map(({label:e,onClick:r,variant:i="primary",disabled:l,withBadge:m},o)=>a(B,{onClick:r,variant:i,size:"md",inline:!0,disabled:l,withBadge:m,children:e},o));return j(a("div",{className:O("efp-modal",`efp-modal--${E}`,{"efp-modal--open":v},w),role:"dialog","aria-modal":"true","aria-labelledby":s?F:void 0,"aria-label":s?void 0:q,ref:p,tabIndex:-1,onClick:c,children:h("div",{className:"efp-modal__box",style:_?{maxWidth:`${_}px`}:void 0,onClick:t=>t.stopPropagation(),children:[h("div",{className:"efp-modal__header",children:[s&&a("div",{className:"efp-modal__title-container",children:a("h2",{className:"efp-modal__title",id:F,children:s})}),a("button",{type:"button",className:"efp-modal__close",onClick:c,"aria-label":y,title:y,children:a("i",{className:"icon-close","aria-hidden":"true"})})]}),a("div",{className:"efp-modal__body",children:D}),(u.length>0||f.length>0)&&h("div",{className:"efp-modal__footer",children:[a("div",{className:"efp-modal__footer-left",children:u.length>0&&x(u)}),f.length>0&&a("div",{className:"efp-modal__footer-right",children:x(f)})]})]})}),A)};export default P;