Руководство по разработке мобильных страниц H5

CSS

предисловие

При разработке обычного мобильного терминала H5 мы неизбежно столкнемся с различными подводными камнями.В этой статье вы увидите, как их решить.Статья длинная, и рекомендуется собрать ее для дальнейшего использования!

Впереди высокая энергия!

Связанные с совместимостью видео В Android прямое использование нативного видео приводит к полноэкранному воспроизведению, охватывающему все элементы, поэтому используйте проигрыватель x5. Однако у плеера x5 есть проблемы, хотя он и не закроет элемент, но добавит свои спецэффекты (закроет слой маски навигационной панели).

<video
  id='live-player'
  controls={false}
  preload="auto"
  playsInline
  mtt-playsinline=”true“
  webkit-playsinline='true'
  x5-video-player-type='h5'
  x5-video-orientation='portrait'
  x5-playsinline='true'
/>

Это позволяет использовать проигрыватель x5 на Android, а свойства playInline и webkit-playsinline включают встроенное воспроизведение на iOS. Однако не очень хорошо устанавливать совместимость встроенного воспроизведения через свойства, поэтому на данный момент нам нужно использовать библиотеку iphone-inline-video, что можно сделать через enableInlineVideo(video).

Холст размыт на экране сетчатки

Просто нужно масштабировать кисть в соответствии с соотношением пикселей

run(canvasEl) {
    const canvas = canvasEl;
    const ctx = canvas.getContext('2d');
    const devicePixelRatio = window.devicePixelRatio || 1;
    const backingStorePixelRatio = ctx.webkitBackingStorePixelRatio ||
    ctx.mozBackingStorePixelRatio ||
    ctx.msBackingStorePixelRatio ||
    ctx.oBackingStorePixelRatio ||
    ctx.backingStorePixelRatio || 1;

    const ratio = devicePixelRatio / backingStorePixelRatio;
    if (devicePixelRatio !== backingStorePixelRatio) {
      const oldWidth = canvas.width;
      const oldHeight = canvas.height;

      canvas.width = oldWidth * ratio;
      canvas.height = oldHeight * ratio;

      canvas.style.width = `${oldWidth}px`;
      canvas.style.height = `${oldHeight}px`;
      ctx.scale(ratio, ratio);
    }
  },

Картинка с таким же масштабом на ПК очень четкая, а на мобиле размытая, в чем причина?

После исследования было обнаружено, что виновником является devicePixelRatio.Поскольку разрешение мобильного телефона слишком маленькое, если веб-страница отображается в соответствии с разрешением, оно будет очень маленьким, поэтому Apple отображает только разрешение 960640 iPhone 4 на веб-странице и отображает только 480320, поэтому devicePixelRatio=2, теперь Android грязный, есть 1,5/2/3 и т. д. Если вы хотите, чтобы изображение отображалось более четко на мобильном телефоне, вы должны использовать 2x фоновое изображение вместо тега img (обычно 2 раза), например, ширина и высота div 100100, фоновое изображение должно быть 200200, а затем background-size:contain;, чтобы отображаемое изображение было яснее; код выглядит следующим образом:

   background:url(../images/icon/all.png) no-repeat center center;
   -webkit-background-size:50px 50px;
   background-size: 50px 50px;
   display:inline-block; 
   width:100%; 
   height:50px;

Включить или отключить автоматическое определение номеров телефонов на страницах;

<meta name="format-detection" content="telephone=no"> 

По умолчанию устройство автоматически распознает любую строку, которая может быть номером телефона. Вы можете отключить эту функцию, установив phone=no. То же самое верно для установки адреса электронной почты и адреса, чтобы они не распознавались.

Проблема установки ввода веб-сайта h5 на type=number

Установка типа ввода веб-страницы h5 на число обычно вызывает три проблемы:

Проблема 1: свойство maxlength работает неправильно

<input type="number" oninput="checkTextLength(this ,10)">
<script type="text/javascript">
    function checkTextLength(obj, length) {
        if(obj.value.length > length)  {
            obj.value = obj.value.substr(0, length);
        }
    }
</script>

Вопрос 2: значение по умолчанию округляется при отправке формы

<input type="number" step="0.01" /> //input中type=number一般会自动生成一个上下箭头,点击上箭头默认增加一个step,点击下箭头默认会减少一个step;number中默认step是1,也就是step=0.01可以允许输入2位小数,并且点击上下箭头分别增加0.01和减少0.01;step和min一起使用时数值必须在min和max之间

Проблема 3. Некоторые телефоны Android имеют проблемы со стилем

Метод удаления стиля ввода по умолчанию:

input,textarea {
    border: 0;
    -webkit-appearance: none; //可同时屏蔽输入框怪异的内阴影,解决iOS下无法修改按钮样式,测试还发现,加了此属性后,iOS下默认还是有圆角的,不过可以用border-radius属性修改
}

выберите проблему с настройками раскрывающегося списка

Проблема 1: Реализация правильного выравнивания

Установите следующие свойства

select option {
    direction: rtl;
}

Проблема 2: отключить стрелку выбора по умолчанию

::-ms-expand修改表单控件下拉箭头,设置隐藏并使用背景图片来修饰

select::-ms-expand { display:none; }

Проблема с автозапуском аудио HTML5 для мобильных устройств

Поскольку веб-страница автоматически воспроизводится аудио или видео. Play Trigger TouchStart Play и Pause (так, чтобы звук запускал загрузку), затем JS, а затем не работает без проблем; решающий код:

document.addEventListener('touchstart', function () {
    document.getElementsByTagName('audio')[0].play();
    document.getElementsByTagName('audio')[0].pause();
});

Страница CSS-анимации мигает белым, анимация зависает, а изображение беспорядочно

1. Максимально используйте синтетические свойства transform и opacity для разработки CSS3-анимации, не используйте левое и верхнее положение для позиционирования.

2. Включите аппаратное ускорение

-webkit-transform: translate3d(0, 0, 0);
-moz-transform: translate3d(0, 0, 0);
-ms-transform: translate3d(0, 0, 0);
transform: translate3d(0, 0, 0);

Плавающие дочерние элементы растягивают высоту поля родительского элемента (BFC)

Обходной путь выглядит следующим образом:

1. Для родительского элемента установлено значение overflow: hidden;

2. родительский элемент для отображения: встроенный блок;et

Два метода здесь заключаются в том, чтобы изменить родительский элемент плавающего элемента на элемент BFC (контекст форматирования на уровне блока), установив свойство css, чтобы высота дочернего элемента могла растянуть родительский элемент; однако это лучше использовать метод 1, потому что элемент встроенного блока будет иметь некоторую ширину и высоту, чтобы растянуть себя

Проблема с кешем туда-обратно

Нажатие резервной копии браузера иногда не запускает js автоматически, особенно в mobilesafari; это связано с возвратным кешем (bfcache), решение:

window.onunload = function(){};

локационная яма

В IOS фиксированное позиционирование не работает, когда виртуальная клавиатура поднята, поэтому мы используем абсолютное вместо абсолютного во время разработки.

проблема с воспроизведением аудиоэлемента и видеоэлемента в ios и android

<audio src="music/bg.mp3" autoplay loop controls>你的浏览器还不支持哦</audio> //音频,写法一
<audio controls="controls"> //音频,写法二   
    <source src="music/bg.ogg" type="audio/ogg"></source>
    <source src="music/bg.mp3" type="audio/mpeg"></source> //优先播放音乐bg.ogg,不支持在播放bg.mp3    
</audio>

Обычно здесь можно слушать музыку, если не работает, то, вероятно, из-за ограничений WeChat.

Вопрос 3: Ограничения Wechat

Если это ограничено WeChat, вам нужно вызвать интерфейс WeChat в это время, и страница сначала представит:

<script src="http://res.wx.qq.com/open/js/jweixin-1.0.0.js"></script>

Затем JS пишет в события WeChat:

document.addEventListener("WeixinJSBridgeReady", function() {
    document.getElementById('music').play();
}, false);

резюме:

1. Атрибут autoplay элемента audio нельзя использовать на IOS и Android, но это нормально на стороне ПК.

2. Когда элемент audio не установлен с помощью элементов управления, он будет занимать место на IOS и Android, но Chrome не будет занимать место на стороне ПК.

Проблема 4: автозапуск Safari

document.addEventListener('touchstart', function(){   
    audio.play();
}, false);

Система ios не поддерживает стиль паузы анимации (состояние воспроизведения анимации)

Страницы H5 обычно содержат фоновую музыку, а также предоставляют вращающийся значок музыки, чтобы пользователи могли включать и выключать музыку; мы надеемся, что когда пользователь нажимает кнопку музыки, значок перестает вращаться, а затем щелкает значок, чтобы продолжить анимацию вдоль позиции. где он остановился раньше; animation-play-state — самый простой способ, но ios не поддерживает

Текущее решение: значок музыки отвечает за запуск анимации, а родительский элемент значка отвечает за запись значения поворота при его остановке.

ios предотвращает выбор элемента страницы с длительным нажатием

Решение: добавление стилей может запретить пользователям копирование, решается как ios, так и общий Android

-webkit-touch-callout:none;  //系统默认菜单被禁用;可以实现页面因为长按弹出各种操作窗口
-webkit-user-select:none; //webkit浏览器  
-khtml-user-select:none; //早期浏览器 
-moz-user-select:none; //火狐 
-ms-user-select:none; //IE10 
user-select:none; 

После добавления этого кода возникнет проблема на IOS.В это время обнаруживается, что поле ввода не может вводить содержимое; причина этого -webkit-user-select:none; Это свойство, решение состоит в том, чтобы одновременно установите его в файле css. Свойства ввода следующие:

input {      
     -webkit-user-select:auto; //webkit浏览器    
}

Как решить зависание/медленность html5 при прокрутке полосы прокрутки вверх и вниз

Во-первых, вы можете добавить height: 100% в html и тело страницы, и тогда это может вызвать проблему скольжения страницы на IOS.

Решение: 1. Сделать html и body фиксированными на 100% (или 100vh), 2. Затем поместите внутри height: 100% div, установите overflow-y: auto и -webkit-overflow-scrolling: touch;

overflow-x:auto имеет проблемы совместимости в iOS, решение:

.scroll-box {
  /* 模态框之类的div不能放在这个容器中,否则关闭模态框有时候关闭不了 */
  height: 100%;
  overflow-y: auto;
  -webkit-overflow-scrolling: touch;
  overflow-scrolling: touch;
}

Как убрать фон или рамку при нажатии на элемент

а, кнопка, ввод, текстовое поле { -webkit-tap-highlight-color: rgba (0,0,0,0); -webkit-user-modify:read-write-plaintext-only; //-webkit-user-modify имеет побочный эффект, заключающийся в том, что метод ввода больше не может вводить несколько символов } или а, кнопка, ввод, текстовое поле { -webkit-tap-highlight-color: rgba (0,0,0,0); }

Браузер назад не обновляется

Это предыдущее столкновение, здесь также сказано; в основном в WebView, когда вы нажимаете на страницу возврата, вместо обновления, это не ваш ожидаемый эффект, решить Метод заключается в использовании JS:

方法1:
window.addEventListener('pageshow', () => {
  if (e.persisted || (window.performance && 
    window.performance.navigation.type == 2)) {
    location.reload()
  }
}, false);

方法2:
window.history.replaceState(null, '', window.location.href + '?timestamp=' + new Date().getTime());

onpageshow срабатывает каждый раз при загрузке страницы, загружается ли она из кеша или загружается нормально, в этом разница между ним и onload; persisted определяет, читается ли страница из кеша

Доступ к страницам осуществляется через историю и вперед и назад. значение типа 2

переход очистить заставку

-webkit-transform-style: preserve-3d; //设置内嵌的元素在 3D 空间如何呈现:保留3D
-webkit-backface-visibility:hidden; //设置进行转换的元素的背面在面对用户时是否可见:隐藏
-webkit-perspective: 1000;

Решить аннулирование активного псевдокласса

<body ontouchstart></body>

Цвет фона верхней строки состояния

apple-mobile-web-app-capable是设置Web应用是否以全屏模式运行;语法:
<meta name="apple-mobile-web-app-capable" content="yes"> //content设置为yesWeb应用会以全屏模式
<meta name="apple-mobile-web-app-status-bar-style" content="black" />

Примечание. Если вы сначала не укажете полноэкранный режим с помощью apple-mobile-web-app-capable, этот метатег не будет иметь никакого эффекта; если для контента установлено значение по умолчанию, строка состояния будет отображаться нормально; если установлено пустое, строка состояния будет иметь черный фон; если установлено пусто-полупрозрачное, строка состояния отображается как черная полупрозрачная; если установлено значение по умолчанию или пусто, страница отображается под строкой состояния, то есть строка состояния занимает верхняя часть; страница занимает нижнюю часть, они не блокируют друг друга и не блокируются; если установлено пусто-полупрозрачное, страница будет заполнять экран, а верхняя часть страницы будет закрыта строкой состояния (это будет покрывать высоту страницы 20 пикселей, в то время как экран Retina iphone4 и itouch4 составляет 40 пикселей); по умолчанию Значение по умолчанию.

ios область

Safari 3D Transform игнорирует уровень z-индекса

В браузере Safari (этот браузер Safari включает Safari на iOS, WeChat на iPhone и Safari на Mac OS X), когда мы используем 3D-преобразование, если элемент-предок не имеет overflow:hidden/ Ограничения, такие как прокрутка/авто, будут напрямую игнорировать настройку порядка наложения z-index самого себя и других элементов и напрямую использовать реальную трехмерную перспективу для рендеринга. Например, в следующей сцене модуль в красной рамке на рисунке использует 3D-преобразование для выполнения анимации вращения, но в браузере Safari z-индекс слоя маски QR-кода игнорируется, и в результате используется реальный -мировая 3D-перспектива для рендеринга. Появились перекрывающиеся баги:

Решение:

Родительский, любой родительский, не основной уровень, установка overflow:hidden восстанавливает тот же рендеринг, что и в других браузерах. Бороться с ядом ядом. Иногда страница сложная, и мы не можем установить overflow:hidden для родителя, тогда мы можем установить достаточно большое значение translateZ для затронутого элемента, например, translateZ(100px).

белый экран ввода ios

Эта проблема, кажется, существует только в ios9

Обходной путь: добавьте относительное позиционирование ввода родительского элемента в строке, это фантастика.

Проблема плохой поддержки ввода событий клавиатуры keyup/keydown/keypress в IOS

После расследования было обнаружено, что метод ввода IOS (будь то сторонний или собственный) может обнаружить клавиатуру английского языка или цифр, но не может обнаружить клавиатуру китайского языка.После ввода китайского языка вам нужно нажать кнопку «Назад». чтобы начать поиск, решение: используйте событие oninput html5 для замены keyup и достижения аналогичного эффекта keyup с помощью следующего кода;

1. Изменено выбранное состояние элемента input:checkbox или input:radio, и изменен атрибут checked.

2. Изменяется значение элемента input:text или textarea, а также изменяется атрибут value.

3. Выбранный элемент элемента select был изменен, и атрибут selectedIndex изменился Унифицированное использование мониторинга ввода

<input type="text" id="testInput">
<script type="text/javascript">
    document.getElementById('testInput').addEventListener('input', function(e){
        var value = e.target.value; //e.target指向事件执行时鼠标所点击区域的那个元素;初学者会认为当前事件所绑定的元素就是鼠标所点击的那个元素,这时就要看看时间绑定的元素内部有没有子元素,如果有e.target指向这个子元素,如果没有e.target和this都指向事件所绑定的元素
    });
</script>

Ввод букв с клавиатуры IOS, решение начальной заглавной буквы по умолчанию

Установите следующие свойства

<input autocapitalize="off" autocorrect="off" />

//Три атрибута ввода являются автозаполнением: по умолчанию включено, что означает, разрешать ли браузеру автоматически записывать вводимое значение.Вы можете добавить autocomplete="off" к вводу, чтобы закрыть запись и сохранить содержимое ввода в секрете; autocapitalize: автоматическое использование заглавных букв, autocorrect: исправление ошибок

По поводу оптимизации шрифтов на iOS и OS X (шрифты жирные и несовместимые на горизонтальном и вертикальном экранах и т.д.)

Размер шрифта будет сброшен, когда браузер iOS находится в альбомной ориентации.Установка text-size-adjust на none может решить проблему на iOS, но функция масштабирования шрифта в настольном Safari не будет работать, поэтому лучшим решением будет установка текста -размер-отрегулировать до 100%

-webkit-text-size-adjust: 100%;
-ms-text-size-adjust: 100%;
text-size-adjust: 100%;

В некоторых случаях некликабельные элементы, такие как (метка, диапазон), прослушивают события щелчка, которые не будут запускаться в ios.

В этом случае просто добавьте строку кода CSS к элементу, который не вызывает событие клика.

cursor: pointer;

ios имеет различную поддержку time date()

var date =new Date("2019/10/21"); 

Отладка показала, что 2019/10/21 эквивалентно 2019-10-21 00:00:00, то есть ios по умолчанию считается от 0, нам не нужно устанавливать следующие часы, минуты и секунды на 00 :00:00

Недопустимое событие щелчка привязки метки iOS (safari)

iOS (safari) иногда привязка события клика к метке недействительна, просто добавьте пустой onclick="", например:<a onclick=""></a>

Страница перехода location.href в ios пуста

Слой setTimeout в пальто location.href решен!

setTimeout(() => {
       window.location.href = 'www.juejin.im'
}, 0);

Исправлена ​​ошибка, когда клавиатура подпрыгивала и падала

Нажмите, чтобы просмотреть

Суммировать

Дорога длинна и дорога длинна, а дорога совместимости все дальше и дальше.