10

我有 page1,它是 index.html,它是一个独立的网站,包括标题和脚本等。我在此页面上有一个按钮,单击该按钮将通过 ajax 加载 page2 并将 page2 插入 page1。Page2 只是其中的 div data-role="page" 和 html,它不是一个独立的页面。但是,url 更改为 page2.html,然后如果我“刷新”页面,它不会加载完整的页面,因为 page2 不是完整的页面,它只是被注入到 page1 中。

我尝试设置 data-url="index.html&dashboard"(dashboard 是 page2 上的主要 id),在这种情况下,url 看起来正确,因为它仍然是 index.html&dashboard,因此即使您在 page2 上,页面刷新也会重新加载 page1。但是现在,jquery 吓坏了并永远坐在加载屏幕上,因为它找不到“仪表板”,因为该内容仅在用户单击按钮后才添加。

我该如何解决这个问题?

谢谢。

page1 index.html

<!DOCTYPE HTML>
<html>
<head>
<title>title</title>
<script><script type="text/javascript" charset="utf-8" src="cordova-1.7.0.js"></script>
<script type="text/javascript" charset="utf-8" src="js/jquery.js"></script>
<script type="text/javascript" charset="utf-8" src="js/jquery.mobile.js"></script>
<script type="text/javascript" charset="utf-8" src="js/global.js"></script>
<script type="text/javascript" charset="utf-8" src="js/login.js"></script>

<link rel="stylesheet" type="text/css" href="css/jquery.mobile.css" />
<link rel="stylesheet" type="text/css" href="css/style.css" />

<script type="text/javascript" charset="utf-8" src="cordova-1.7.0.js"></script>
<script type="text/javascript" charset="utf-8" src="js/jquery.js"></script>
<script type="text/javascript" charset="utf-8" src="js/jquery.mobile.js"></script>
<script type="text/javascript" charset="utf-8" src="js/login.js"></script>

<link rel="stylesheet" type="text/css" href="css/jquery.mobile.css" />
<link rel="stylesheet" type="text/css" href="css/style.css" />

</head>
<body>
    <div data-role="page" data-theme="b">

        <div data-role="header" data-theme="b">
            <h1>Login</h1>
        </div>
        <!-- /header -->

        <div data-role="content">
            <div class="row">
                <label for="login_name">Login Name:</label> <input
                    class="ui-input-text" type="text" name="login_name" id="login_name" />
            </div>
            <div class="row">
                <label for="basic">Password:</label> <input class="ui-input-text"
                    type="password" name="password" id="password" />
            </div>
            <div class="row">
                <input type="checkbox" name="remember" id="remember" class="custom"
                    data-mini="true" /> <label for="remember">Remember Me</label>
            </div>
            <div class="row">
                <input type="submit" id="submit" name="submit" value="Submit" />
            </div>
        </div>
        <!-- /content -->

    </div>
    <!-- /page -->
</body>
</html>

page2仪表板.html

<div id="dashboard" data-role="page" data-theme="b" data-url="index.html&dashboard">

<div data-role="header" data-theme="b">
    <h1 id="page_title">Dashboard</h1>
</div>

登录.js

$(function() {


$("#submit").click(function() {

    if ($("#login_name").val() == "") {
        alert("Please enter a login name");
        return false;
    }

    if ($("#password").val() == "") {
        alert("Please enter a password");
        return false;
    }

    $.post(URL + 'login', {
        'APIKEY' : APIKEY,
        'login' : $("#login_name").val(),
        'password' : $("#password").val()
    }, function(data) {
        if (data.error == "") {

            $.mobile.changePage("dashboard.html", { transition : "slide" });
        } else {
            alert(data.error);
        }

    }, "json");

});

});

4

1 回答 1

7

简答

简短的回答是 jQuery Mobile 希望您使用散列来表示单个页面的状态:

  • /index.html - 第 1 页
  • /index.html#dashboard - 仪表板。

相反,当您应该只是调用 JavaScript 来动态更改第一页上的内容以表示第二页时,您正在加载一个全新的页面。

如果简短的回答有意义,那就太好了!如果不是,那么长答案非常详细,并描述了解决此问题的两种方法。

长答案

您本质上要问的是如何构建一个多页面移动网站,并让两个页面都可以通过标识资源的 URI 访问。

您可以使用两种方法来解决此问题。

多页模板:

对于 jQuery mobile,这是通过jQuery Mobile Multi-page Template完成的。

一般的想法是您的两个页面都在同一个 HTML 文档中,如下所示:

<head>

</head>

<!-- This is your FIRST page -->
<div data-role="page" id="one">

    <div data-role="header">
        <h1>Multi-page</h1>
    </div><!-- /header -->

    <div data-role="content" >  
        <h2>One</h2>

        <p>I have an id of "one" on my page container. I'm first in the source order so I'm shown when the page loads.</p>  

        <h3>Show internal pages:</h3>
        <p><a href="#two" data-role="button">Show page "two"</a></p>    
        <p><a href="#popup"data-role="button" data-rel="dialog" data-transition="pop">Show page "popup" (as a dialog)</a></p>
    </div><!-- /content -->

    <div data-role="footer" data-theme="d">
        <h4>Page Footer</h4>
    </div><!-- /footer -->
</div><!-- /page one -->

<!-- This is your SECOND page -->
<!-- Start of second page: #two -->
<div data-role="page" id="two" data-theme="a">

    <div data-role="header">
        <h1>Two</h1>
    </div><!-- /header -->

    <div data-role="content" data-theme="a">    
        <h2>Two</h2>
        <p>I have an id of "two" on my page container. I'm the second page container in this multi-page template.</p>   
        <p>Notice that the theme is different for this page because we've added a few <code>data-theme</code> swatch assigments here to show off how flexible it is. You can add any content or widget to these pages, but we're keeping these simple.</p>  
        <p><a href="#one" data-direction="reverse" data-role="button" data-theme="b">Back to page "one"</a></p> 

    </div><!-- /content -->

    <div data-role="footer">
        <h4>Page Footer</h4>
    </div><!-- /footer -->
</div><!-- /page two -->

</body>

接下来,jQuery Mobile 本质上是使用 CSS 隐藏 id="two" 的 DIV 元素,只显示 id="one" 的 div。当用户点击 `href="#two" 的超链接时,有一个侦听器会拦截 hashChange 事件并触发一些 JavaScript 代码来隐藏 id="one" 的 DIV 并显示 id="two" 的 DIV ”。

这使得页面转换看起来非常流畅和快速,无需访问服务器来获取 HTML 标记。

动态受保护的内容:

如果您的数据更加动态,那么另一种选择是使用jQuery Mobile 动态页面注入。这个过程的一般前提与多页面模板类似,浏览器监听 hashChange 事件,除了改变页面外,它还向服务器发出 AJAX 请求以检索 JSON 内容。

<div id="home" data-role="page">
  <div data-role="header"><h1>Categories</h1></div>
  <div data-role="content">
    <h2>Select a Category Below:</h2>
    <ul data-role="listview" data-inset="true">
        <li><a href="#category-items?category=animals">Animals</a></li>
        <li><a href="#category-items?category=colors">Colors</a></li>
        <li><a href="#category-items?category=vehicles">Vehicles</a></li>
    </ul>
  </div>

</div>

单击“动物”类别时,隐藏 id="home" DIV。在此示例中,不是重新加载页面,而是动态生成 HTML 并使用 JSON 对象的结果填充。

这是处理显示正确内容的代码:

// Load the data for a specific category, based on
// the URL passed in. Generate markup for the items in the
// category, inject it into an embedded page, and then make
// that page the current active page.
function showCategory( urlObj, options )
{
    var categoryName = urlObj.hash.replace( /.*category=/, "" ),

        // Get the object that represents the category we
        // are interested in. Note, that at this point we could
        // instead fire off an ajax request to fetch the data, but
        // for the purposes of this sample, it's already in memory.
        category = categoryData[ categoryName ],

        // The pages we use to display our content are already in
        // the DOM. The id of the page we are going to write our
        // content into is specified in the hash before the '?'.
        pageSelector = urlObj.hash.replace( /\?.*$/, "" );

    if ( category ) {
        // Get the page we are going to dump our content into.
        var $page = $( pageSelector ),

            // Get the header for the page.
            $header = $page.children( ":jqmData(role=header)" ),

            // Get the content area element for the page.
            $content = $page.children( ":jqmData(role=content)" ),

            // The markup we are going to inject into the content
            // area of the page.
            markup = "<p>" + category.description + "</p><ul data-role='listview' data-inset='true'>",

            // The array of items for this category.
            cItems = category.items,

            // The number of items in the category.
            numItems = cItems.length;

        // Generate a list item for each item in the category
        // and add it to our markup.
        for ( var i = 0; i < numItems; i++ ) {
            markup += "<li>" + cItems[i].name + "</li>";
        }
        markup += "</ul>";

        // Find the h1 element in our header and inject the name of
        // the category into it.
        $header.find( "h1" ).html( category.name );

        // Inject the category items markup into the content element.
        $content.html( markup );

        // Pages are lazily enhanced. We call page() on the page
        // element to make sure it is always enhanced before we
        // attempt to enhance the listview markup we just injected.
        // Subsequent calls to page() are ignored since a page/widget
        // can only be enhanced once.
        $page.page();

        // Enhance the listview we just injected.
        $content.find( ":jqmData(role=listview)" ).listview();

        // We don't want the data-url of the page we just modified
        // to be the url that shows up in the browser's location field,
        // so set the dataUrl option to the URL for the category
        // we just loaded.
        options.dataUrl = urlObj.href;

        // Now call changePage() and tell it to switch to
        // the page we just modified.
        $.mobile.changePage( $page, options );
    }
}

另请注意,在查看 Category 页面和 Animals 页面的 URL 时,您可以看到 HTML 文档每次都是相同的。不同的是哈希值。

http://jquerymobile.com/demos/1.1.0/docs/pages/dynamic-samples/sample-reuse-page.html

http://jquerymobile.com/demos/1.1.0/docs/pages/dynamic-samples/sample-reuse-page.html#category-items?category=animals

当页面加载时,哈希值用于表示页面的状态。由于浏览器大多是无状态的,哈希是我们可以用来帮助确定页面应该向用户显示什么状态的一种技巧。

只需将您的 changePage 方法调用与类别页面菜单中使用的 URL 进行比较:

<li><a href="#category-items?category=animals">Animals</a></li>
<li><a href="#category-items?category=colors">Colors</a></li>
<li><a href="#category-items?category=vehicles">Vehicles</a></li>

请注意,当用户单击链接时,唯一改变的是哈希值,页面永远不会重新加载。但在您的示例中,您实际上正在加载一个全新的页面:

// this is a new page, not a hash
$.mobile.changePage("dashboard.html", { transition : "slide" });

从逻辑上讲,您需要重新考虑如何表示页面的策略。要充分利用 jQuery Mobile,请将您的第一个 HTML 页面视为所有 CSS、JavaScript 和静态内容的框架。

之后,您请求的任何资源都应由具有相同页面的 URL 标识,后跟哈希值。

例如,如果您的静态页面是“index.html”,那么您的仪表板可能是“index.html#dashboard”。您也可以在 id="dashboard" DIV 中包含仪表板 HTML 并使用来自服务器的数据动态填充它,或者您可以通过 AJAX 加载 HTML 和数据。

第二点是任何直接访问您的仪表板的人都需要访问“/index.html#dashboard”,这将加载您的原始页面,触发一些 JavaScript 来检查哈希,识别它包含“仪表板”,然后制作通过拉回动态数据转换到仪表板页面。

有关更多信息,请参阅jQuery 页面动态文档

于 2012-05-12T06:28:01.280 回答