简体   繁体   中英

jQuery Mobile: How to run a callback-function before $.mobile.changePage?

I'm setting up a mobile app with jQuery Mobile and PhoneGap. What I want to do is that when I click link with id "news_link" I want jQuery to fetch data from database and put it to jQm's collapsible set. In my solution, I've wanted to use $.mobile.changePage inside callback functions because I want to wait until the data has been fetched and put inside the container before the code changes page. Here's the code:

$(function() { 
  $('#news_link').click(function(){
    loadNewsFromDB(function(){
       $.mobile.changePage( $("#news"), { transition: "slideup"} );
    });
});

loadNewsFromDB is PhoneGap's SQLite database function which would fetch the data with more callback functions from database. The contents would be put to desired container with .html-function

function loadNewsFromDB(){
//some code here
theDB.transaction(function(tx) {
    tx.executeSql(sqlStr, [], onLoadNewsSuccess, onLoadNewsError);
},onTxError, onTxSuccess);

function onLoadNewsSuccess(tx, results){
    //some code here
    $("#newsSet").html(htmlCodeAndContentToPut);

Html is jQm's basic ui-modules:

<!-- some html code here --!>
<div data-role="page" id="news">
    <div data-role="content">
        <div id="newsSet" data-role="collapsible-set" data-mini="true">

With debugging I know that the code work up until it works very well unti it arrives to $.mobile.changePage-function. Somehow it doesn't change the page. I've checked the function it works well in other occasions, but not inside callback-functions.

I would be very grateful if someone would give me a hand am I not seeing something obviously wrong or is something more specific? What other workarounds there is for fetching the data from SQLite, waiting for data to be fetched, putting the data to container and then changing the pages?

  • I never had problems with $.mobile.changePage on callback-function from Ajax , so it is possible to change page from a callback-function
  • You call the loadNewsFromDB function with a function as a parameter.
    But I can't see where/how you are using this parameter on the loadNewsFromDB function itself. Don't you have to define the parameter on the loadNewsFromDB function?
    After defining the callback-function, you should call it when your data is ready.
  • I would try to use the $.mobile.changePage directly in your onLoadNewsSuccess function.

I believe that the code should look like this:

function loadNewsFromDB(callback){
//some code here
theDB.transaction(function(tx) {
    tx.executeSql(sqlStr, [], function(tx, result) {
            ...some code here...;
            if (callback) {
                callback();
            }    
        },onLoadNewsError);
},onTxError, onTxSuccess);

Edit:
To answer the question in the comments:

  • In your $(function() code, you are adding listener for the $('#news_link').click event.
  • In this listener, you tell Jquery to call loadNewsFromDB function and to send it the following callback-function as a parameter: function(){ $.mobile.changePage( $("#news"), { transition: "slideup"} .

Sending the callback function is not enough, you should use it (call it) in your code.
To use it, I did the following:

  • Changed the function definition function loadNewsFromDB(callback)
    now, it does have a new paramter: callback (which is the name you can use to call back your callback-function).

  • In your loadNewsFromDB function, you are calling the transaction function, and send it 3 parameters: inline function , onTxError, onTxSuccess.
    your inline function just call the tx.executeSql function and send it 4 parameters: sqlStr, [], onLoadNewsSuccess, onLoadNewsError .
    I changed the third parameter.
    Instead of calling the onLoadNewsSuccess function, I wrote the needed function inline

  • In the inline function, I checked if the callback function exist if (callback)
    If it exist, I called it! callback();
    calling the callback function, should change the page...

Do you mean right before the changePage fires?

Then use the pagebeforechange event, which is triggered right before the changePage . I'm using this:

  $(document).on( "pagebeforechange", function( e, data ) {
  // do stuff
  console.log( e )
  console.log( data )
  });

for all my changePage redirects. The data object will contain all changePage parameters (like toPage, options.fromPage...), so you can pretty much re-config the changePage call to your need.

EDIT : Also beware this event fires twice if pushstate is enabled. One event is triggered by the actual transition (on hashChange), this will pass the toPage you are going to as string . The 2nd event will be triggered by pushState and will pass the toPage as object . You can define what to when by checking for:

 typeof data.toPage == 'string'

EDIT : In your specific case, I would preventDefault() the original changePage depending on how long it takes to fetch the data from your database. It would probably be best to preventDefault , trigger your database call from inside pageBeforeChange and when you have the data loaded, trigger a new changePage. For more info see this example from the JQM docs.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM