原生开发移动web单页面(step by step)6——history api应用

简介: 以上几篇的内容成功的将多页面合成到单页面上,然而还是有很多区别的, 多页面切换的时候,通过浏览器的自带后退前进键可以进行导航,然而到目前为止,是没有办法进行的导航的,这一篇主要是引入了这个功能。

以上几篇的内容成功的将多页面合成到单页面上,然而还是有很多区别的, 多页面切换的时候,通过浏览器的自带后退前进键可以进行导航,然而到目前为止,是没有办法进行的导航的,这一篇主要是引入了这个功能。

在进入正题之前,我们还需要对整体做一下调整, 一般情况下, 一个页面分为两个部分,一部分是静态部分,只要起到布局作用,还有一部分为改变部分,主要用来切换页面的作用。在布局中设置一块改动的区域,放置动态页面, 不同的动态页面调用静态部分提供的方法来调整不同的布局。 这样的结构如下图所示。

界面的布局

这里的做法就是让静态布局部分和动态部分都是Page实例对象,通过App的实例对象初始化并渲染首页,如以下代码:

app.initialize(staticPage, indexPage);

切换页面的代码与之前的一样, 介绍了这个后,接下来介绍history api。

浏览器history记录是类似一个数组, 通过一个索引值代表当前的页面,如果按后退键,将会索引值减一, 跳到之前的页面,按前进键则相反,如下图所示。


history栈

浏览器history api提供了两个方法来操作这个历史数据的数组: pushState和replaceState。 pushState方法的作用为在当前页面所在的索引值插入一个新的记录,然后移除所有后面的记录,与用户单击一个链接大致相同, 并将历史的索引值转到新的记录。如下图所示


pushState操作

replaceState方法的作用为替换当前的记录,不影响历史记录数组中其它数据的更改,如下图所示


replaceState操作

当点击浏览器的前进后退键的时候,就会触发popstate的事件, 通过监听事件获取到的历史数组中状态的改变而动态更改页面,调用history的方法也会触发popstate事件。
下面介绍了如何把它集成到App对象中,App构造函数的代码如下

function App() {
    this.currentPage = null;
    this.staticPage = null;
    this.pageContainer = null;
    this.routeObj = {};
}

staticPage存放静态布局页面,可以调用其方法更改外部布局
pageContainer是可变页面的容器
routeObj对象放置页面对象,key代表页面的url, value为Page对象
nitialize方法代码如下

initialize: function (staticPage, indexPage) {
    staticPage = this.staticPage = staticPage || App.emptyPage;
    var that = this;

    staticPage.render(function (html) {
        var body = document.body;
        body.insertAdjacentHTML("afterbegin", html);
        staticPage._initialize(body);
        if (staticPage.domList.pageContainer) {
            that.pageContainer = staticPage.domList.pageContainer;
        }
        else {
            console.error("staticPage must have pageContainer");
        }
        that.render(indexPage, true);

        window.addEventListener("popstate", function (ev) {
            if (ev.state && ev.state.data) {
                var url = ev.state.data;
                var page = that.routeObj[url];
                that._renderPage(page);
            }
        }, false);
    });
},

这里需要静态布局页面有个PageContainer,让动态页面放置。
_attachHistory方法的代码如下

_attachHistory: function (page, isBack) {
    var newUrl =  page.url;
    
    if (isBack) {
        history.replaceState({data: newUrl}, "", newUrl);
    }
    else {
        history.pushState({data: newUrl}, "", newUrl);
    }
},

_renderPage方法的代码如下

_renderPage: function (page) {
    if (this.currentPage) this.currentPage._dispose();
    this.currentPage = page;
    page.app = this;

    document.title = page.title;
    var pageContainer = this.pageContainer;
    page.render(function (html) {
        pageContainer.innerHTML = html;
        page._initialize(pageContainer);
    });
}

修改Page构造函数与App.createPage函数
Page构造函数如下

function Page(title, url) {
    this.title = title;
    this.url = url;
    this.domList = {};
    this.eventList = [];
}

App.createPage代码如下

App.createPage = function (title, url, options) {
    var page = new Page(title, url);
    App.extend(page, options);
    return page;
}

然后对应创建一个App.emptyPage, 代码如下

App.emptyPage = App.createPage("", "", {
    render: function (fn) {
        fn("<div class='pageContainer'></div>");
    },
    getDomObj: function (dom) {
        this.attachDom(".pageContainer", "pageContainer", dom);
    }
});

修改entry.js, login.js, register.js和goal.js,定义各自Page实例对象的时候,增加url的字段,
分别为/serve/entry, /serve/login, /serve/register和/serve/goal, 以serve开头的,是为了页面刷新的时候,服务器检索到url以/serve开头,然后跳转到首页。

更改提供后台服务页面的serverFile.js修改exports.getFile方法,代码如下

exports.getFile = function (req, res, key, root) {
    if (key.indexOf("/public/")  === 0) {
        serveFile(req, res, root + key, root);
    }
    else if (key.indexOf("/serve") === 0) {
        serveFile(req, res, root + "/public/serve/index.html", root);
    }
    else {
        res.statusCode = 404;
        res.end("404");
    }
}

修改index.js的代码,如下

var app = new App();
app.initialize(null, entryPage);

如果想要刷新跳到当前页面,那就需要在类似在sessionStorage的存储机制中存放当前的页面url,然后在初始化的时候,将entryPage替换为该url的page对象即可。

总结: 加入history api后,页面表现和普通的多页面相差无几了,可以跳转, 可以后退。 改变页面后title和url也随着改变,刷新直接跳到首页也可以跳到当前页。到了这篇为止,单页面改造完毕,然而,单页面的灵活性远非多页面可比的, 如果处理得到,复杂性却不会增加很多。 接下来的篇章就是为了让单页面更加出彩, 甚至达到原生app的水准。

后续更新:下一篇将重点介绍css3的animation, 配合页面切换, 让页面切换动态化。css3的animation模块在后面的部分使用的非常频繁,为理解后面的代码做一下基础。

案例链接


原生开发移动web单页面(step by step)1——传统页面的开发
原生开发移动web单页面(step by step)2——Page对象
原生开发移动web单页面(step by step)3——App对象
原生开发移动web单页面(step by step)4——tap事件与slide事件
原生开发移动web单页面(step by step)5——nodejs服务器的搭建

相关文章
|
4天前
|
开发框架 JavaScript 前端开发
TypeScript 是一种静态类型的编程语言,它扩展了 JavaScript,为 Web 开发带来了强大的类型系统、组件化开发支持、与主流框架的无缝集成、大型项目管理能力和提升开发体验等多方面优势
TypeScript 是一种静态类型的编程语言,它扩展了 JavaScript,为 Web 开发带来了强大的类型系统、组件化开发支持、与主流框架的无缝集成、大型项目管理能力和提升开发体验等多方面优势。通过明确的类型定义,TypeScript 能够在编码阶段发现潜在错误,提高代码质量;支持组件的清晰定义与复用,增强代码的可维护性;与 React、Vue 等框架结合,提供更佳的开发体验;适用于大型项目,优化代码结构和性能。随着 Web 技术的发展,TypeScript 的应用前景广阔,将继续引领 Web 开发的新趋势。
18 2
|
9天前
|
API 开发工具 开发者
探究亚马逊国际获得AMAZON商品详情 API 接口功能、作用与实际应用示例
亚马逊提供的Amazon Product Advertising API或Selling Partner API,使开发者能编程访问亚马逊商品数据,包括商品标题、描述、价格等。支持跨境电商和数据分析,提供商品搜索和详情获取等功能。示例代码展示了如何使用Python和boto3库获取特定商品信息。使用时需遵守亚马逊政策并注意可能产生的费用。
|
14天前
|
监控 搜索推荐 安全
探究亚马逊详情API接口:开发与应用
在数字化时代,亚马逊作为全球领先的电商平台,为商家和消费者提供了丰富的商品信息和便捷的购物体验。本文深入探讨了亚马逊详情API接口的获取与运用,帮助开发者和商家实时监控商品数据、分析市场趋势、优化价格策略、分析竞争对手、构建推荐系统及自动化营销工具,从而在竞争中占据优势。文章还提供了Python调用示例和注意事项,确保API使用的安全与高效。
43 3
|
18天前
|
搜索推荐 数据挖掘 API
API接口在电商的应用及收益
本文探讨了API接口技术在电商领域的应用及其带来的收益。API接口作为连接电商平台与外部系统的桥梁,实现了高效、实时的数据交换和集成,提升了用户体验、运营效率和市场竞争力。具体应用包括库存管理、支付网关、物流跟踪、自动化业务流程、个性化推荐和精准营销等方面。通过实战案例分析,展示了亚马逊和小型电商公司如何利用API接口实现自动化管理,提高了工作效率和客户满意度。未来,API接口技术将更加注重智能化、标准化、安全性和跨界合作。
54 3
|
18天前
|
前端开发 API 开发者
Python Web开发者必看!AJAX、Fetch API实战技巧,让前后端交互如丝般顺滑!
在Web开发中,前后端的高效交互是提升用户体验的关键。本文通过一个基于Flask框架的博客系统实战案例,详细介绍了如何使用AJAX和Fetch API实现不刷新页面查看评论的功能。从后端路由设置到前端请求处理,全面展示了这两种技术的应用技巧,帮助Python Web开发者提升项目质量和开发效率。
33 1
|
21天前
|
XML 安全 PHP
PHP与SOAP Web服务开发:基础与进阶教程
本文介绍了PHP与SOAP Web服务的基础和进阶知识,涵盖SOAP的基本概念、PHP中的SoapServer和SoapClient类的使用方法,以及服务端和客户端的开发示例。此外,还探讨了安全性、性能优化等高级主题,帮助开发者掌握更高效的Web服务开发技巧。
|
20天前
|
JSON 安全 API
虾皮商品详情API接口:获取与应用
虾皮(Shopee)作为东南亚领先的电商平台,为商家和开发者提供了丰富的API接口服务,尤其是商品详情API接口。该接口能够快速获取商品的详细信息,包括标题、价格、库存、描述、图片、规格参数、销量、用户评价等。本文将详细介绍虾皮商品详情API接口的功能、特点、获取方法及应用场景,并给出使用时的注意事项。
40 0
|
JavaScript Java Serverless
入门 | 云开发平台1分钟开发一个API
云开发系列课程主要介绍了从入门到精通快速上手Serverless和云开发技术。学习内容涵盖云开发协同、云函数、云数据库、多媒体托管、前后端一体化框架等Serverless Web开发必备知识。希望通过云开发系列课程的学习与实际操作,让大家深入了解Serverless和云开发技术,并加深对阿里云云开发平台和阿里云Serverless产品的理解与认识。 本篇内容作为入门知识,让你在一分钟之内运行起一个Java/NodeJS/Python/PHP任何一门语言的Serverless API ,让你可以在后续的课程中向API添加各种有意思的功能。
入门 | 云开发平台1分钟开发一个API
|
12天前
|
JSON API 数据格式
淘宝 / 天猫官方商品 / 订单订单 API 接口丨商品上传接口对接步骤
要对接淘宝/天猫官方商品或订单API,需先注册淘宝开放平台账号,创建应用获取App Key和App Secret。之后,详细阅读API文档,了解接口功能及权限要求,编写认证、构建请求、发送请求和处理响应的代码。最后,在沙箱环境中测试与调试,确保API调用的正确性和稳定性。
|
24天前
|
供应链 数据挖掘 API
电商API接口介绍——sku接口概述
商品SKU(Stock Keeping Unit)接口是电商API接口中的一种,专门用于获取商品的SKU信息。SKU是库存量单位,用于区分同一商品的不同规格、颜色、尺寸等属性。通过商品SKU接口,开发者可以获取商品的SKU列表、SKU属性、库存数量等详细信息。
下一篇
无影云桌面