Window.resize из-за виртуальной клавиатуры вызывает проблемы с jQuery mobile
Я сталкиваюсь с необычной проблемой, и я ищу предложения. В основном, я использую:
- JQuery Mobile 1.1
- JQuery 8.2
- PhoneGap (Cordova) 2.1
На многих страницах моего приложения на iPhone, если я помещаю курсор в поле ввода, это открывает виртуальную клавиатуру. Это прекрасно и ожидается.
Здесь проблема: в некоторых случаях (но не все), помещая мой курсор в поле ввода, запускается событие window.resize. Я проверил это с помощью кода ниже:
$(window).resize(function(e) {
alert('The window resize occurred! Width: ' + $(window).width() + " Height: " + $(window).height());
debugger;
return false;
});
Сразу же после разрешения события window.resize JQueryMobile решает изменить размер страницы до неправильной высоты. Я могу сказать, что это страница, потому что я добавил другую границу цвета для каждого элемента, чтобы узнать, что именно. И во многих случаях это изменение размера приводит к тому, что половина моего графического интерфейса переполняется под дном div, иногда даже заставляя мой курсор скрываться под div.
Лучший способ понять это с помощью скриншота:
![window.resize() triggering page resize]()
Теперь я действительно не ожидаю, что кто-то найдет для вас точный ответ. Я просто ищу советы для отладки. Я добавил оператор "debugger" в мое событие window.resize() и попытался выполнить код. Я надеялся привлечь другого слушателя с изменением размера, который предназначен для изменения размера страницы. Если я могу это найти, я могу временно нанести вред, когда кто-то выбирает элемент формы, а затем снова разрешает изменение размера при размытии или изменении ориентации. Проблема в том, что я прошел через каждую строку кода, и процесс отладки остановился прямо до изменения размера.
Это заставляет меня задаться вопросом, есть ли другое событие, уволенное в стороне от window.resize. Поэтому я добавил две строки ниже:
document.addEventListener("throttledresize", function() { alert("throttledresize fired.") }, false);
document.addEventListener("orientationchange", function() { alert("orientationchange fired.") }, false);
Тем не менее, никто не стрелял. Поэтому я немного застрял. У меня хорошее чувство, что я знаю, в чем проблема, но я не могу отследить его до источника. Любые предложения о том, где я могу найти этот таинственный код, который изменяет размер страницы на window.resize()?
Ответы
Ответ 1
Я рад видеть, что я не сумасшедший! Я рад сообщить, что я реализовал довольно хорошее решение. Вот шаги, если вы хотите сделать то же самое:
1) Перейдите в jquery.mobile-1.x.x.js
2) Найдите $.mobile = $.extend() и добавьте следующие атрибуты:
last_width: null,
last_height: null,
3) Измените getScreenHeight для работы следующим образом:
getScreenHeight: function() {
// Native innerHeight returns more accurate value for this across platforms,
// jQuery version is here as a normalized fallback for platforms like Symbian
if (this.last_width == null || this.last_height == null || this.last_width != $( window ).width())
{
this.last_height = window.innerHeight || $( window ).height();
this.last_width = $(window).width();
}
return this.last_height;
}
В основном это предотвратит пересчет высоты страницы, если ширина не изменится. (т.е. изменение ориентации). Поскольку мягкая клавиатура влияет только на высоту, этот метод вернет кешированное значение вместо измененной высоты.
Я собираюсь создать отдельное сообщение, чтобы спросить, как правильно переопределить метод $.mobile.getScreenHeight. Я попытался добавить код ниже в отдельный JS файл, но он не сработал:
delete $.mobile.getScreenHeight;
$.mobile.last_width = null;
$.mobile.last_height = null;
$.mobile.getScreenHeight = function()
{
... the code listed above
}
Он запускал большую часть времени, но также запускал исходную функцию. Странно как-то. Я разместил отдельную тему о том, как правильно распространять $.mobile здесь: Правильный способ переопределить метод JQuery Mobile в $.mobile
Ответ 2
У меня была аналогичная проблема, попробуйте это:
$('#main-browse').bind("orientationchange", function(event) {
//Put the page dimensions for example with minimum height property
}
Ответ 3
У меня была такая же проблема в Cordova (3.x) с использованием JQuery Mobile 1.4 - так что это не то, что может быть рассмотрено авторами библиотеки. Я пробовал много разных решений, но никто этого не исправил. Ближайший кандидат включал привязку простых обработчиков, связанных с событиями "throttleresize" и "showhow" на объектах окна и документа, соответственно.
Тем не менее, я все еще потерял "запертое" чувство пользовательского интерфейса, и пользователь мог перетащить весь мой пользовательский интерфейс после выхода из клавиатуры. Конечно, верхний и нижний колонтитулы не двигались, но мой фон и основная область содержимого теперь перетаскивались, и появлялись полосы прокрутки. Полностью неприемлемо, если вы пытаетесь почувствовать это родное приложение...
Итак, я решил посмотреть в Firebug Chrome/Safari и узнать, куда добавляются дополнительные пиксели в модель окна. Как ни странно, я заметил, что изменение высоты не происходит вообще, в моем случае это была прокладка на активной странице. поэтому я адаптировал решение из другой публикации Stack:
function resetActivePageHeight() {
var aPage = $( "." + $.mobile.activePageClass ),
aPagePadT = parseFloat( aPage.css( "padding-top" ) ),
aPagePadB = parseFloat( aPage.css( "padding-bottom" ) ),
aPageBorderT = parseFloat( aPage.css( "border-top-width" ) ),
aPageBorderB = parseFloat( aPage.css( "border-bottom-width" ) );
aPage.css( "min-height", deviceInfo.height - aPagePadT - aPagePadB - aPageBorderT - aPageBorderB )
.css("top","0px").css("padding","0px");}
Затем я привязал их к событиям документа и окна на готовом устройстве.
$( document ).bind( "pageshow", resetActivePageHeight );
$( window ).bind( "throttledresize", resetActivePageHeight );
Опять же, хотя я хотел бы взять кредит, я думаю, что я просто нашел дополнительный угол для кого-то другого.
Ответ 4
перейдите в ваш файл androidmanifest и в действии измените или обновите это значение
андроид: windowSoftInputMode = "adjustResize"
Я знаю, что adjustPan разбивает страницу таким образом, что элементы управления скрыты. по умолчанию (неуказано) может быть нормально, и здесь есть другие варианты.
я думаю, что если он не изменяет размер, он не сообщает jqm, что kb показан
так что оставляйте jqm как есть, без ваших изменений, и он выполнит свою работу
Кстати, я использую cordova 2.2, jqm 1.2 и jquery 1.8.2
Ответ 5
У меня возникла проблема, когда виртуальная клавиатура расширила область просмотра, показывая содержимое внизу (внешняя панель).
Я решил установить высоту css в зависимости от высоты окна:
$('#page').css('height', $(window).height());