Oracle JET 单页面应用程序Router 使用(上)

  单页面应用程序:使用一个进加载一次的网页,如果页面由于用户的交互而改变,则仅绘制更改的页面部分。

  要创建单页面应用程序需要使用 oj.Router 的虚拟导航来支持,ojModule 用来响应页面的重新绘制。 ojModule 仅用于分离的 view 和 viewMode ,使之与页面通过 Knockout绑定。另外,ojModule 可选,当不使用分离视图与模型时,可直接在元素上响应变化。

  1.简单模型:

  

  当选择 Chapter1 或其他时,将显示新内容,并且URL更改以反映用户在页面上当前的位置。

  

  2.路由器适配器

  路由器带有两个URL适配器。每个适配器定义如何将URL格式化表示。

    urlPathAdapter:在路径段中格式化 URL 。每个段都是的当前状态 id ,由 ‘ / ’ 分隔,如: localhost:8000/chap1

    urlParamAdapter:使用查询参数格式化 URL 。每个参数都是路由器名称及其当前状态 id ,如:localhost:8000/?root=chap1

  路由器的默认适配器是 urlPathAdapter 。需要更改可以使用 方法:

    oj.Router.defaults[‘urlAdapter‘] = new oj.Router.urlParamAdapter

  当路由单页应用程序时,页面不会从头开始加载,但页面内容会动态更改。为了成为浏览器历史的一部分并提供书签内容,Oracle JET 路由器模拟使用 HTML5 历史记录推送状态功能导航的行为。路由器还控制 URL 看起来像传统页面 URL。 这些 URL 没有资源,必须设置 HTML 服务器。这是通过一个重写引擎的简单规则完成的。

  一般来说,当应用程序中用户需求只包含几个视图并且关联状态不是很复杂,则使用查询参数。而路径段显示 URL 则显得 URL 更简洁,特别是使用嵌套路径(添加子路由)。

  ojModule 与 oj.Router 结合使用,可以配置 ojModule 对象,其中模块名称是路由器的状态。当路由器更改状态时,ojModule 将自动加载并呈现当前 RouterState 对象的值得指定模块内容。

  3.简单使用例子:

  (1)appController.js:

define([‘ojs/ojcore‘, ‘knockout‘, ‘ojs/ojknockout‘, ‘ojs/ojrouter‘, ‘ojs/ojbutton‘, ‘ojs/ojtoolbar‘],
  function(oj, ko) {
    function ControllerViewModel() {
      var self = this;

      self.router = oj.Router.rootInstance;
      self.router.configure({
        ‘pref‘: { label: ‘Preface‘, isDefault: true},
        ‘chap1‘: { label: ‘Chapter 1‘},
        ‘chap2‘: { label: ‘Chapter 2‘},
        ‘chap3‘ : {label: ‘Chapter 3‘}
      });
      oj.Router.defaults[‘urlAdapter‘] = new oj.Router.urlParamAdapter;
    }

    return new ControllerViewModel();
  }
);

  a)添加 ojrouter 模块。

      ‘ojs/ojrouter‘

  b)创建路由实例,oj.Router.rootInstance 表示唯一根路由,该路由的名称是 “root” 。

      self.router = oj.Router.rootInstance;

  c)配置路由器状态,属性: label:链接字符串,没有定义标题属性时,用于页面的标题。

                 value:与该状态相关联的对象。

                 isDefault:设置起始页面 

      self.router.configure({
            ‘pref‘: { label: ‘Preface‘, isDefault: true},
            ‘chap1‘: { label: ‘Chapter 1‘},
            ‘chap2‘: { label: ‘Chapter 2‘},
            ‘chap3‘ : {label: ‘Chapter 3‘}
          });

  d)URL适配器,可选。   

      oj.Router.defaults[‘urlAdapter‘] = new oj.Router.urlParamAdapter;

  (2)main.js

require([‘ojs/ojcore‘, ‘knockout‘, ‘appController‘, ‘ojs/ojknockout‘, ‘ojs/ojrouter‘, ‘ojs/ojmodule‘],
  function (oj, ko, app) {
    $(function() {
        oj.Router.sync().then(
          function() {
            ko.applyBindings(app, document.getElementById(‘routingContainer‘));
          },
          function(error) {
            oj.Logger.error(‘Error in root start: ‘ + error.message);
          }
        );
    });
  }
);

  a)添加 ojrouter 模块和 ojmodule(需要使用 ojmodule 时添加)

      ‘ojs/ojrouter‘, ‘ojs/ojmodule‘

  b)将路由器与当前 URL 同步。必须在路由器配置后才能调用,以将 URL 与路由器状态同步。   

      oj.Router.sync().then()

  c)将 appController 挂载到 HTML 上

      ko.applyBindings(app, document.getElementById(‘routingContainer‘))

  (3)index.html

  <div id="routing-container">
      <div id=‘buttons-container‘ data-bind="ojComponent: {component:‘ojToolbar‘}">
        <div data-bind="ojComponent: { component: ‘ojButtonset‘,
                                        checked: router.stateId,
                                        focusManagement: ‘none‘}">
          <!-- ko foreach: router.states -->
            <label data-bind="attr: {for : id}"></label>
            <input type="radio" name="chapter" data-bind="value: id,
                                                          attr: { id: id},
                                                          ojComponent: { component: ‘ojButton‘,
                                                                          label: label}"/>
          <!-- /ko -->
        </div>
      </div>
      <div data-bind="ojModule: router.moduleConfig"></div>
    </div>

  a)选择时触发状态转换

    定义 checked 属性给予 router.stateId 观察值。它使用双向绑定。当点击一个按钮时,id 被写入到 stateId 中,使路由器状态转换。

  b)观察状态并更新相关部分

      data-bind="ojModule: router.moduleConfig"

    使用需要创建相应的 views 和 viewModels

    

  c) router.states 可以获取到路由配置转化的数组以供遍历展示内容

  

  (4)实际效果如前简单模型相同。

  4.使用子路由

  (1)appController.js

define([‘ojs/ojcore‘, ‘knockout‘, ‘ojs/ojknockout‘, ‘ojs/ojrouter‘, ‘ojs/ojbutton‘, ‘ojs/ojtoolbar‘, ‘ojs/ojnavigationlist‘],
  function(oj, ko) {
    function ControllerViewModel() {
      var self = this;
      // 创建根路由
      self.shapeRouter = oj.Router.rootInstance;
      self.shapeRouter.configure({
        ‘square‘: { label: ‘Square‘, isDefault: true },
        ‘circle‘: { label: ‘Circle‘ },
        ‘oval‘: { label: ‘Oval‘}
      });
      // 创建子路由配置
      self.colorRouter = self.shapeRouter.createChildRouter(‘color‘).configure({
        ‘red‘: { label: ‘Red‘, isDefault: true },
        ‘blue‘: { label: ‘Blue‘ },
        ‘green‘: {label: ‘Green‘}
      });
      self.menuItemSelect = function(event, ui) {
        self.shapeRouter.go(ui.item.children(‘a‘).text());
      }
    }

    return new ControllerViewModel();
  }
);

  a)创建根路由

  b)创建子路由并配置

    使用 createChildRouter(‘name‘) 创建子路由并添加 configure 配置。

  (function(event, ui) 这里的 ui 是 jqueryui 的内容。ui 为当前选择的对象,ui.item获得对象的元素,这里为 ul)

  (2)main.js 与上例相同

  (3)index.html

<div id="routing-container">
    <!-- 导航栏部分 -->
      <div id="toolbar" data-bind="ojComponent: { component: ‘ojToolbar‘}">
     <!-- 父路由导航栏部分 --> 
        <div data-bind="ojComponent: { component: ‘ojButtonset‘,
                                       checked: shapeRouter.stateId,
                                       focusManagement: ‘none‘ }">
          <!-- ko foreach: shapeRouter.states -->
            <label data-bind="attr: {for: id}"></label>
            <input type="radio" name="shape" data-bind="value: id, attr: { id: id},
                                                        ojComponent: {component: ‘ojButton‘,
                                                                      label: label}"></input>
          <!-- /ko -->
        </div>
     <!-- 直接跳转指定位置 -->
        <button id="menuButton" data-bind="ojComponent: { component: ‘ojButton‘, label: ‘Go to‘,
                                                          menu: ‘#gotoMenu‘}">

        </button>
     <!-- 列表显示跳转位置 --> 
        <ul id="gotoMenu" style="display: none" data-bind="ojComponent: { component: ‘ojMenu‘,
                                                                           select: menuItemSelect }">
          <!-- ko foreach: shapeRouter.states -->
            <li>
              <a data-bind="text: label"></a>
              <ul data-bind="foreach: $root.colorRouter.states">
                <li>
                  <a data-bind="text: ‘/‘ + $parent.id + ‘/‘ + id"></a>
                </li>
              </ul>
            </li>
          <!-- /ko -->
        </ul>
      </div>
      <hr/>
    <!-- 展示部分 -->
      <div id="pageContent" class="oj-flex oj-flex-items-pad">
     <!-- 子路由导航栏 -->
        <div class="oj-xl-2 oj-lg-2 oj-md-2 oj-sm-12 oj-flex-item">
          <div id="colors" data-bind="ojComponent: { component: ‘ojNavigationList‘,
                                                     selection: colorRouter.stateId,
                                                     drillMode: ‘none‘}">
            <ul data-bind="foreach: colorRouter.states">
              <li data-bind="attr: {id: id}">
                <a data-bind="text: label"></a>
              </li>
            </ul>
          </div>
        </div>
     <!-- 图形显示 -->
        <div class="oj-xl-10 oj-md-10 oj-sm-12 oj-flex-item">
          <div data-bind="css: shapeRouter.stateId(), style: { background: colorRouter.stateId() }"></div>
        </div>
      </div>
    </div>

  a)stateId 可以让 knockout 观察,而 steteId() 则可以读取当前的 Id 的值。

  (4)CSS

.square { width: 100px; height: 100px; }
.circle { width: 100px; height: 100px;
          -moz-border-radius: 50px;
          -webkit-border-radius: 50px;
          border-radius: 50px; }
.oval   { width: 200px; height: 100px;
          -moz-border-radius: 100px / 50px;
          -webkit-border-radius: 100px / 50px;
          border-radius: 100px / 50px; }

  (5)效果显示:

      

时间: 2024-10-04 13:23:20

Oracle JET 单页面应用程序Router 使用(上)的相关文章

【Web API系列教材】1.3 — 实战:用ASP.NET Web API和Angular.js创建单页面应用程序(下)

练习2:创建SPA界面 在本练习中,你将首先创建Geek Quiz的web前端,使用AngularJS专注于单页面应用程序的交互.然后你将使用CSS3来执行丰富的动画和提供一个当从一个问题转换到另一个问题时切换上下文的可视化效果以加强用户体验. 任务1:使用AngularJS来创建SPA界面 在本任务中,你将使用AngularJS来实现Geek Quiz应用程序的客户端.AngularJS是一个开源的JavaScript框架,它能够搭配MVC以加强基于浏览器的应用程序,使其对于开发和测试都更加便

SPA 单页面应用程序。

看到这个问题,先说下自己的理解到的程度,再去参考做修正,争取这一次弄懂搞清楚 自己的理解: 单页面应用程序,解决浏览器获取数据刷新页面的尴尬,通过ajax请求获取数据达到异步更新视图的按钮,原理的实现由两种, 其一,通过hash值的变化,绑定onhashchange的回调函数更新视图,因为hash值的变化不会让页面失去响应,不会向服务器发送请求.下面列出几种可能改变hash值的方法,改变url中的hash.浏览器回退按钮可能出现历史记录中的url包含的hash值不一样,都将触发该事件:还有触发带

Vue系列(1):单页面应用程序

前言:关于页面上的知识点,如有侵权,请看 这里 . 关键词:SPA.单个 HTML 文件.全靠 JS 操作.Virtual DOM.hash/history api 路由跳转.ajax 响应.按需加载.MVVM SPA 我们先来看一下在百科上面的解释吧,emmmm,一般呢,我每次搜索一些不懂的词,都会习惯先去看百科里面的解释,反正我从来都不奢望能看懂,只是指望有个大概的框架的,哈哈~ "单页面应用(SPA:single-page application),就是只有一张Web页面的应用,是加载单个

通过Blazor使用C#开发SPA单页面应用程序(4) - Ant Design Button

前面学习了Blazor的特点.环境搭建及基础知识,现在我们尝试的做个实际的组件. Ant Design是蚂蚁金服是基于Ant Design设计体系的 UI 组件库,主要用于研发企业级中后台产品.目前官方是基于React和Angular实现的,今年也推出了Vue的实现.其组件涵盖面较广,其组件风格及交互效果还是比较惊艳的,后面准备利用Ant Design的样式文件利用Blazor模仿几个组件的实现. 由于也是新学的Blazor开发,可能实现的方式有些笨拙,希望高手提出宝贵意见,先看看实现的Butt

[后端人员耍前端系列]KnockoutJs篇:使用WebApi+Bootstrap+KnockoutJs打造单页面程序

一.前言 在前一个专题快速介绍了KnockoutJs相关知识点,也写了一些简单例子,希望通过这些例子大家可以快速入门KnockoutJs.为了让大家可以清楚地看到KnockoutJs在实际项目中的应用,本专题将介绍如何使用WebApi+Bootstrap+KnockoutJs+Asp.net MVC来打造一个单页面Web程序.这种模式也是现在大多数公司实际项目中用到的. 二.SPA(单页面)好处 在介绍具体的实现之前,我觉得有必要详细介绍了SPA.SPA,即Single Page Web App

Vue单页面应用

单页面应用指一个系统只加载一次资源,然后下面的操作交互.数据交互是通过router.ajax来进       行,页面并没有刷新:<1>在vue搭建的环境里面怎么有没有公用的css和js?如果有是怎么引用的? 有公用的css和js,有两种引用的方法:(要深刻理解单页面应用程序哦,单页面就是引入后在哪里都能使用) 1.全局公共引用样式和js文件 2.组件的引入 单页面的应用优点: 1.分离前后端关注点,前端负责界面显示,后端负责数据存储和计算.不会把前后端的逻辑混杂在一起: 2.减轻服务器压力,

详细解剖大型H5单页面应用的核心技术点

阐述下项目 Xut.js 开发中一个比较核心的优化技术点,这是一套平台代码,并非某一个插件功能或者框架可以直接拿来使用,核心代码大概是6万行左右(不包含任何插件) .这也并非一个开源项目,不能商业使用,只是为了作者开发方便同步修改代码而上传的源码 描述下,项目提出的概念“无需程序员编程”可批量制作app应用.分2大块,1块是客户端(PPT),默认扩展插件提供用户编辑的界面,平台会把设计逻辑与界面数据编译成前端数据资源包(前端能处理的js.css.图片等资源了),另一个大块就是纯前端部分(Xut.

vue单页面条件下添加类似浏览器的标签页切换功能

在用vue开发的时候,单页面应用程序,而又有标签页这种需求,各种方式实现不了, 从这个 到这个,然后再返回上面那个 因为每个标签页的route不一样,导致组件重新渲染的问题,怎么都不知道如何实现......... 简直郁闷到爆炸,后来和同学谈起的时候,说起生命周期这个才恍然大悟, 对于vue的生命周期,因为用的少,本身多用的是created,mounted这两个,都忘记beforeDestroy这些了,然后抓瞎了好久 实现方式是 每次销毁组件之前   缓存数据    能够用到的是 this.$d

SPA设计与架构-理解单页面Web应用 (埃米顿.A斯科特) 中文pdf扫描版

SPA 开发技术的运用是当今Web 开发领域的热门趋势,但真正全面掌握该技术的开发者并不多.本书详尽阐述单页面Web 应用(SPA)开发技术,从SPA 构建基础入手,通过MV*.模块化编程.路由.模块间通信.服务器端交互等概念的阐述,全面介绍SPA 的设计与架构,帮助读者正确掌握SPA 开发的各方面知识要素.同时,<SPA设计与架构:理解单页面Web应用>中还讨论了SPA 的单元测试及客户端任务自动化,覆盖了从开发到部署的一系列任务,让读者在阅读完<SPA设计与架构:理解单页面Web应用