1. iOS 滑动不流畅
  2. iOS 上拉边界下拉出现白色空白
  3. 页面放大或缩小不确定性行为
  4. click 点击穿透与延迟
  5. 软键盘弹出将页面顶起来、收起未回落问题
  6. iPhone X 底部栏适配问题
  7. 保存页面为图片和二维码问题和解决方案
  8. 微信公众号 H5 分享问题
  9. H5 调用 SDK 相关问题及解决方案
  10. H5 调试相关方案与策略

六:iPhone X系列安全区域适配问题

现象:头部刘海两侧区域或者底部区域,出现刘海遮挡文字,或者呈现黑底或白底空白区域。
原因:iPhone X 以及它以上的系列,都采用刘海屏设计和全面屏手势。头部、底部、侧边都需要做特殊处理。才能适配 iPhone X 的特殊情况。
解决方案:设置安全区域,填充危险区域,危险区域不做操作和内容展示。

具体操作为:viewport-fit meta 标签设置为 cover,获取所有区域填充。判断设备是否属于 iPhone X,给头部底部增加适配层
设置 viewport-fit 为 cover
<meta name="viewport" content="width=device-width, initial-scale=1.0, user-scalable=yes, viewport-fit=cover">

增加适配层
使用 safe area inset 变量

/* 适配 iPhone X 顶部填充*/
@supports (top: env(safe-area-inset-top)){
  body,
  .header{
      padding-top: constant(safe-area-inset-top, 40px);
      padding-top: env(safe-area-inset-top, 40px);
      padding-top: var(safe-area-inset-top, 40px);
  }
}
/* 判断iPhoneX 将 footer 的 padding-bottom 填充到最底部 */
@supports (bottom: env(safe-area-inset-bottom)){
    body,
    .footer{
        padding-bottom: constant(safe-area-inset-bottom, 20px);
        padding-bottom: env(safe-area-inset-bottom, 20px);
        padding-top: var(safe-area-inset-bottom, 20px);
    }
}

safe-area-inset-top, safe-area-inset-right, safe-area-inset-bottom, safe-area-inset-left safe-area-inset-*由四个定义了视口边缘内矩形的 top, right, bottom 和 left 的环境变量组成,这样可以安全地放入内容,而不会有被非矩形的显示切断的风险。对于矩形视口,例如普通的笔记本电脑显示器,其值等于零。对于非矩形显示器(如圆形表盘,iPhoneX 屏幕),在用户代理设置的四个值形成的矩形内,所有内容均可见。

其中 env() 用法为 env( <custom-ident> , <declaration-value>? ),第一个参数为自定义的区域,第二个为备用值。
其中 var() 用法为 var( <custom-property-name> , <declaration-value>? ),作用是在 env() 不生效的情况下,给出一个备用值。
constant() 被 css 2017-2018 年为草稿阶段,是否已被标准化未知。而其他iOS 浏览器版本中是否有此函数未知,作为兼容处理而添加进去。

七: 保存页面为图片和二维码问题和解决方案

现象:在工作中有需要将页面生成图片或者二维码的需求。可能我们第一想到的,交给后端来生成更简单。但是这样我们需要把页面代码全部传给后端,网络性能消耗太大。
解决方案 :
1.生成二维码,
使用 QRCode,等插件生成二维码

import QRCode from 'qrcode';
// 使用 async 生成图片
const options = {};
const url = window.location.href;
async url => {
  try {
    console.log(await QRCode.toDataURL(url, options))
  } catch (err) {
    console.error(err);
  }
}
将 await QRCode.toDataURL(url, options) 赋值给 图片 url 即可

2.生成图片
主要是使用 html2Canvas.js 生成 canvas 画布
import html2canvas from 'html2canvas';
html2canvas(document.body).then(function(canvas) {
    document.body.appendChild(canvas);
});

我们使用一个新的 canvas 方法多倍生成,放入一倍容器里面,达到更加清晰的效果,通过超链接下载图片 下载文件简单实现,更完整的实现方式之后更新

const scaleSize = 2;
const newCanvas = document.createElement("canvas");
const target = document.querySelector('div');
const width = parseInt(window.getComputedStyle(target).width);
const height = parseInt(window.getComputedStyle(target).height);
newCanvas.width = width * scaleSize;
newCanvas.height = widthh * scaleSize;
newCanvas.style.width = width + "px";
newCanvas.style.height =width + "px";
const context = newCanvas.getContext("2d");
context.scale(scaleSize, scaleSize);
html2canvas(document.querySelector('.demo'), { canvas: newCanvas }).then(function(canvas) {
  // 简单的通过超链接设置下载功能
  document.querySelector(".btn").setAttribute('href', canvas.toDataURL());
}

当然入如果html中包含oss或者cdn图片,会出现跨域行为,此时需要将网络资源图片转为base64的图片,如:

// 需要跨域请求的列表
      let imgList = [
        {id: '#ossImage1', value: $("#ossImage1").attr('src')},
        {id: '#ossImage2', value: $("#ossImage2").attr('src')}
      ];

      // // pamoise 初始化请求图片
      Promise.all(imgList.map((item) => getBas64(item.value))).then(result => {
        // 返回的图片列表,重新渲染到页面上
        result.forEach((v, k) => {
          $(imgList[k].id).attr('src', v);
        });

      });

/**
       * 图片转base64格式
       */
      /**
       * @description: 图片转base64
       * @param {String} url 需要转换的图片原链接(http://....jpg)
       * @param {String} outputFormat 转换出来的图片的类型(canvas支持jpg/png格式)
       * @return: 返回图片对应的base64编码
       */
      function getBas64(url, outputFormat = 'image/jpg') {
        return new Promise(function (resolve, reject) {
          let canvas = document.createElement('CANVAS'),
            ctx = canvas.getContext('2d'),
            img = new Image;
          img.crossOrigin = 'Anonymous'; // 重点!设置image对象可跨域请求
          img.onload = function () {
            canvas.height = img.height;
            canvas.width = img.width;
            ctx.drawImage(img, 0, 0);
            let dataURL = canvas.toDataURL(outputFormat);
            canvas = null;
            resolve(dataURL);
          };
          // img.src = url; // 旧的方式
          img.src = url + '?t=' + new Date().valueOf() // 防止oss的缓存问题
        })
      }