Подтвердить что ты не робот

Панель jQuery Mobile 1.3 не работает после изменения страницы

Кажется, у меня проблемы с программным открытием и закрытием панели JQM 1.3.

EDIT: это для JQM 1.3.x не 1.4 +

Немного сложно объяснить, поэтому я просто сделал скрипку:)

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

Как реплицировать:

  • Перейти к Fiddle
  • В Fiddle откройте панель и перейдите на страницу Two
  • На странице Two откройте панель и перейдите на страницу One
  • Попробуйте открыть панель сейчас на первой странице, она ничего не делает.

Браузеры, затронутые:

РЕДАКТИРОВАТЬ: Это, похоже, исправлено в Chrome 30.0.1599.101 м

  • Chrome 28.0.1500.95 m
  • IE 10.0.9200.16635
  • Safari//Latest Ver
  • Android WebView (4.2.2)

Браузеры не затронуты:

  • Firefox 23
  • Opera 12.16

Ссылка на скрипт:

http://jsfiddle.net/q2YH3/

Ссылка на другие сообщения

https://github.com/jquery/jquery-mobile/issues/6308

http://forum.jquery.com/topic/panel-not-responding-after-page-change

EDIT: Так что Firefox дает мне ошибку, которую не делают ни Chrome, ни IE.

Когда я нажимаю, чтобы вернуться к первой странице, я получаю:

Type Error: elem is undefined

Ошибка вызывается JQ 1.9.1, я возвращаю ее обратно:

A method for determining if a DOM node can handle the data expando
    acceptData: function( elem ) {
        // Do not set data on non-element because it will not be cleared (#8335).
        if ( elem.nodeType && elem.nodeType !== 1 && elem.nodeType !== 9 ) {
            return false;
        }

        var noData = elem.nodeName && jQuery.noData[ elem.nodeName.toLowerCase() ];

        // nodes accept data unless otherwise specified; rejection can be conditional
        return !noData || noData !== true && elem.getAttribute("classid") === noData;
    }
`

Обратите внимание:

Не устанавливайте данные на неэлемент, потому что он не будет очищен (# 8335).

Ссылка на Github: https://github.com/jquery/jquery/pull/1232

Код OG:

$('.showMenu').on('click', function(){
$.mobile.loading('hide');
$.mobile.activePage.find('#'+$.mobile.activePage.attr('id')+'P').panel("toggle");
});

$('.btnMenuItem').on('click', function(event){
myPgActions.nav(event, function(target){
    $.mobile.changePage(target);
}, false);
});   

var myPgActions = {};

myPgActions = {
nav: function(event, callback, manualHash){
    var PID = $.mobile.activePage.attr('id'),
    target = (!!event) ? event.target.name : manualHash;    
    $("#"+PID+"P").panel( "close" );
    if(PID != 'loading') $("#"+PID+"Iframe").hide();        

    if(PID == target){
        $("#"+PID+"Iframe").hide('fast', function(){
            $("#"+PID+"Iframe").attr('src', "");

            myPgActions.update(PID, target, 'refresh', function(target){
                callback(target)
            });
        }); 

    }else{

        this.update(PID, target, 'change', function(target){
            callback(target);
        });

    }

},// end get

update: function(PID, target, type, updateCallback){

    var ifReady = $.Deferred();

    if(type == 'refresh'){

        this.buildUrl(PID, function(url){

            $('#'+PID+'Iframe').attr( 'src', url);
            ifReady.resolve();          

            $.when(ifReady).then(function(){
                updateCallback('#'+PID+'Iframe')        
            });
        });

    }else if(type == 'change'){

        this.buildUrl(target, function(url){
            $('#'+target+'Iframe').attr( 'src', url);
            ifReady.resolve();
        });

        $.when(ifReady).then(function(){
            updateCallback('#'+target); 
        });
    }
}, // end set
buildUrl: function(page, buildCallback){
    switch(page){
        case 'dash':        
            var mobileSiteUrl = 'URL with options for iframe'
            setTimeout(function(){buildCallback(mobileSiteUrl);},25);
        break;
        case 'local':
            var mobileSiteUrl = 'URL with options for iframe'
            setTimeout(function(){buildCallback(mobileSiteUrl);},25);   
        break;


    }// End Switch
}
}// End Obj
4b9b3361

Ответ 1

Была та же проблема, панель не отображается после изменения страницы.

Два небольших изменения могут исправить это:

я сделал, чтобы сменить панель с id= "myPanel" на class= "myPanel", а затем изменил вызов на панель, чтобы открыть: $('. myPanel: visible'). panel ('open'); - это!

Проблема заключается в том, что панель должна находиться внутри страницы jQuery, и после перехода, если у вас есть панель, установленная на целевой странице, у вас на самом деле есть две (или более) панели с одним и тем же идентификатором , который является неправильным или тем же классом , который является хорошим. Таким образом, вы просто меняете идентификатор на класс и вызываете видимый.

Взял меня слишком долго, надеюсь, это сэкономит время кому-то другому.

Ответ 2

Я немного поиграл с вашим кодом. Я заметил, что если я поставлю предупреждение внутри вашей функции обновления, это все исправит. Поэтому я исследовал, почему предупреждение будет делать работу программы, и нашел эту страницу. http://ubuntuforums.org/archive/index.php/t-930002.html

"Вероятно, вам следует знать, что оценка JavaScript относится к типу" смотреть вперед ": script уже выполняется, когда он все еще оценивается (и пока сама страница все еще оценивается). Вот почему это рекомендуется сбрасывать все ссылки на скрипты в разделе вашей страницы, так как это приведет к полной оценке JavaScript до того, как вы (обычно) можете вызвать функцию (обработчики событий) и, следовательно, избегать глупых ошибок

Теперь alert(); вызов имеет 2 эффекта: (1) он всплывает окно сообщения (пока это так хорошо); но (2) он останавливает поток, используемый JavaScript! Однако браузер других потоков по-прежнему будет продолжать работать (HTML-рендеринг...). Таким образом, это может быть один из тех случаев, когда вам будет полезен более элегантный метод остановки, который должен выполнять только этот (часть) script, когда документ полностью загружен; "

Решение, которое они предлагают, помещает ваш script внутрь. Или используя функцию stateChanged() для HTTP-запроса ajax ".

Ответ 3

Хорошо, я поддержал пост @A.sharif, когда он получил вращение в моей голове.

Проблема заключается в том, что обратный вызов функции "BuildUrl" выполнялся до того, как была создана переменная URL.

Я думал, что позволил достаточно времени с 25ms, но это не так. Я наткнулся на время до того, как обратный вызов будет выполнен до 600 мс, и теперь он отлично работает.

Я уверен, что есть более элегантное решение, но это то, что я получил;)

Новая скрипта:

http://jsfiddle.net/t8zyQ/

Было изменено значение 25 в setTimeout() до 600.

Измененный код:

buildUrl: function(page, buildCallback){
    switch(page){
        case 'dash':        
            var mobileSiteUrl = 'URL with options for iframe'
            setTimeout(function(){buildCallback(mobileSiteUrl);},600);
        break;
        case 'local':
            var mobileSiteUrl = 'URL with options for iframe'
            setTimeout(function(){buildCallback(mobileSiteUrl);},600);  
        break;


    }// End Switch