美文网首页工作生活
打开弹框,背景位置固定

打开弹框,背景位置固定

作者: 奋斗的小小小兔子 | 来源:发表于2019-07-16 15:38 被阅读0次

一、打开弹框时,背景位置固定,弹窗可滚动

  • 给body添加样式 position: fixed; width: 100%;就可以固定背景,不许背景滚动,但这个时候会直接定位到顶部
  • 为了解决上述直接定位到顶部的问题,可以记录弹框打开之前的位置,给body添加样式的同时设置body距离顶部的距离
  • 最后,关闭弹框时,删除body的样式

style.scss

.modal-wrapper {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 100%;
    height: 100%;
    position: fixed;
    background: rgba(0, 0, 0, 0.6);
    top: 0;
    bottom: 0;
    left: 0;
    right: 0;
    z-index: 1999;
  }

  .page-hidden {
    position: fixed;
    width: 100%;
  }

  .hide {
    display: none;
  }

index.jsx

import 'babel-polyfill';
import React, { useState, useEffect } from 'react';

 // [document.scrollingElement兼容性处理](https://github.com/yangg/scrolling-element)
import 'scrolling-element';

 // 设置style兼容性处理
import { setStyle } from '../../../libs/utils';  

import './style.scss';  

const modalWrapper = (WrappedComponent) => {
  const hoc = (props) => {
    const [scrollTop, setScrollTop] = useState(0);

    const allowBodyScrolling = () => {
      setStyle(document.body, { top: '0px' });
      document.body.classList.remove('page-hidden');
      // 在给页面设置了doctype的时候,documentElement.scrollTop(1)/body.scrollTop(2), safari不支持(1), chrome不支持(2)
      if (scrollTop > 0) {
        if (document.scrollingElement) { 
          document.scrollingElement.scrollTop = scrollTop;
        } else {
          document.body.scrollTop = scrollTop;
          document.documentElement.scrollTop = scrollTop;
          window.pageYOffset = scrollTop;
        }
      }
    };

    const forbidBodyScrolling = () => {
      let top = document.scrollingElement ? document.scrollingElement.scrollTop : Math.max(window.pageYOffset, document.documentElement.scrollTop, document.body.scrollTop);
      setScrollTop(top);
      setStyle(document.body, { top: `${-top}px` });
      document.body.classList.add('page-hidden');
    };

    useEffect(() => {
      if (props.config.show) {
        forbidBodyScrolling();
      } else {
        allowBodyScrolling();
      }
    }, [props.config.show]);

    return (
      <div className={`modal-wrapper${props.config.show ? '' : ' hide'}`}>
        <WrappedComponent {...props} />
      </div>
    );
  };

  return hoc;
};

export default modalWrapper;



setStyle.png

export const setStyle = (element, params = {}) => {
  if (!element) return;
  if (Object.getOwnPropertyDescriptor(document.body.style, 'font-size').writable) { // 检查style对象的属性是否可编辑
    Object.keys(params).forEach((key) => {
      element.style[key] = params[key];
    });
  }
  let cssText = element.style.cssText;
  const tmpArr = cssText.split(';');
  let existAttributes = {};
  tmpArr.forEach((item) => {
    let res = item.split(':');
    if (res && res.length > 1) {
      let key = res[0].trim();
      let value = res[1].trim();
      existAttributes[key] = value;
    }
  });
  element.style.cssText = Object.keys(existAttributes).map(key => `${key}: ${existAttributes[key]}`).join(';');
};


使用方法

const Modal = ({ config }) => {
  const { show, onClose, onOk, imgSrc } = config;
  return (
     <div className="modal">
        <img className="close-btn" onClick={onClose} />
        <div className="content" >
          <img className="img" alt="img" src={imgSrc} />
          <div className="button" onClick={onOk}>我知道了</div>
        </div>
      </div>
  );
};
export default modalWrapper(Modal);

相关文章

网友评论

    本文标题:打开弹框,背景位置固定

    本文链接:https://www.haomeiwen.com/subject/egvgcctx.html